From f3a2e03a6bebf383e4668e9759e31d24027f32d9 Mon Sep 17 00:00:00 2001 From: Ben Sander Date: Wed, 10 Feb 2016 09:29:29 -0600 Subject: [PATCH 01/56] Initial commit --- hipamd/README.md | 2 ++ 1 file changed, 2 insertions(+) create mode 100644 hipamd/README.md diff --git a/hipamd/README.md b/hipamd/README.md new file mode 100644 index 0000000000..91165785bb --- /dev/null +++ b/hipamd/README.md @@ -0,0 +1,2 @@ +# HIPIFY +The CLANG-based HIPIFY tool - translates CUDA to HIP From 9d10ae4325bc6a4c8be555934a6d877e5c63c545 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Wed, 10 Feb 2016 20:20:11 +0300 Subject: [PATCH 02/56] Initial version of CLANG based HIPIFY tool for CUDA -> HIP sources conversion --- hipamd/CMakeLists.txt | 42 ++++ hipamd/README.md | 10 +- hipamd/src/Cuda2Hip.cpp | 526 ++++++++++++++++++++++++++++++++++++++++ 3 files changed, 577 insertions(+), 1 deletion(-) create mode 100644 hipamd/CMakeLists.txt create mode 100644 hipamd/src/Cuda2Hip.cpp diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt new file mode 100644 index 0000000000..6d727c70be --- /dev/null +++ b/hipamd/CMakeLists.txt @@ -0,0 +1,42 @@ +cmake_minimum_required(VERSION 2.8.8) + +project(hipify) + +find_package(LLVM REQUIRED PATHS ${LLVM_DIR} NO_DEFAULT_PATH) + +message(STATUS "Found LLVM ${LLVM_PACKAGE_VERSION}") +message(STATUS "Using LLVMConfig.cmake in: ${LLVM_DIR}") + +include_directories(${LLVM_INCLUDE_DIRS}) +link_directories(${LLVM_LIBRARY_DIRS}) +add_definitions(${LLVM_DEFINITIONS}) + +# Now build our tools +add_executable(hipify src/Cuda2Hip.cpp) + +# Link against LLVM and CLANG tools libraries +target_link_libraries(hipify + clangASTMatchers + clangFrontend + clangTooling + clangParse + clangSerialization + clangSema + clangEdit + clangLex + clangAnalysis + clangDriver + clangAST + clangToolingCore + clangRewrite + clangBasic + LLVMSupport + LLVMMCParser + LLVMMC + LLVMBitReader + LLVMOption + LLVMCore) + +set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_CFLAGS}") +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS}") +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -std=c++11 -pthread -D __STDC_LIMIT_MACROS -D __STDC_CONSTANT_MACROS -D __STDC_FORMAT_MACROS -fno-rtti -fvisibility-inlines-hidden") diff --git a/hipamd/README.md b/hipamd/README.md index 91165785bb..a813325e65 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -1,2 +1,10 @@ # HIPIFY -The CLANG-based HIPIFY tool - translates CUDA to HIP +The CLANG-based HIPIFY tool - translates CUDA to [HIP](https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP/blob/master/README.md) + +# How to Build +- Get LLVM and CLANG sources and build CLANG, then install it to a **LLVM_INSTALL_PATH** folder +- make build dir for hipify and run the folloing commands there: +``` +> cmake -DLLVM_DIR="LLVM_INSTALL_PATH" path_to_hipify_src +> make +``` diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp new file mode 100644 index 0000000000..c4c8f58810 --- /dev/null +++ b/hipamd/src/Cuda2Hip.cpp @@ -0,0 +1,526 @@ +/* +Copyright (c) 2015-2016 Advanced Micro Devices, Inc. All rights reserved. + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +*/ +/** + * @file Cuda2Hip.cpp + * + * This file is compiled and linked into clang based hipify tool. + */ +#include "clang/ASTMatchers/ASTMatchers.h" +#include "clang/ASTMatchers/ASTMatchFinder.h" +#include "clang/Basic/SourceManager.h" +#include "clang/Frontend/FrontendActions.h" +#include "clang/Lex/Lexer.h" +#include "clang/Tooling/CommonOptionsParser.h" +#include "clang/Tooling/Refactoring.h" +#include "clang/Tooling/Tooling.h" +#include "llvm/Support/CommandLine.h" +#include "llvm/Support/MemoryBuffer.h" +#include "llvm/Support/Signals.h" +#include "llvm/Support/Debug.h" +#include "clang/Frontend/TextDiagnosticPrinter.h" +#include "clang/Rewrite/Core/Rewriter.h" +#include "clang/Lex/MacroInfo.h" +#include "clang/Frontend/CompilerInstance.h" +#include "clang/Lex/Preprocessor.h" +#include "clang/Lex/PPCallbacks.h" + +#include +#include + +using namespace clang; +using namespace clang::ast_matchers; +using namespace clang::tooling; +using namespace llvm; + +#define DEBUG_TYPE "cuda2hip" + +namespace { + struct hipName { + hipName() { + // defines + cuda2hipRename["__CUDACC__"] = "__HIPCC__"; + + // includes + cuda2hipRename["cuda_runtime.h"] = "hip_runtime.h"; + cuda2hipRename["cuda_runtime_api.h"] = "hip_runtime_api.h"; + + // Error codes and return types: + cuda2hipRename["cudaError_t"] = "hipError_t"; + cuda2hipRename["cudaError"] = "hipError_t"; + cuda2hipRename["cudaSuccess"] = "hipSuccess"; + + cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; + cuda2hipRename["cudaErrorMemoryAllocation"] = "hipErrorMemoryAllocation"; + cuda2hipRename["cudaErrorMemoryFree"] = "hipErrorMemoryFree"; + cuda2hipRename["cudaErrorUnknownSymbol"] = "hipErrorUnknownSymbol"; + cuda2hipRename["cudaErrorOutOfResources"] = "hipErrorOutOfResources"; + cuda2hipRename["cudaErrorInvalidValue"] = "hipErrorInvalidValue"; + cuda2hipRename["cudaErrorInvalidResourceHandle"] = "hipErrorInvalidResourceHandle"; + cuda2hipRename["cudaErrorInvalidDevice"] = "hipErrorInvalidDevice"; + cuda2hipRename["cudaErrorNoDevice"] = "hipErrorNoDevice"; + cuda2hipRename["cudaErrorNotReady"] = "hipErrorNotReady"; + cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; + + // error APIs: + cuda2hipRename["cudaGetLastError"] = "hipGetLastError"; + cuda2hipRename["cudaPeekAtLastError"] = "hipPeekAtLastError"; + cuda2hipRename["cudaGetErrorName"] = "hipGetErrorName"; + cuda2hipRename["cudaGetErrorString"] = "hipGetErrorString"; + + // Memcpy + cuda2hipRename["cudaMemcpy"] = "hipMemcpy"; + cuda2hipRename["cudaMemcpyHostToHost"] = "hipMemcpyHostToHost"; + cuda2hipRename["cudaMemcpyHostToDevice"] = "hipMemcpyHostToDevice"; + cuda2hipRename["cudaMemcpyDeviceToHost"] = "hipMemcpyDeviceToHost"; + cuda2hipRename["cudaMemcpyDeviceToDevice"] = "hipMemcpyDeviceToDevice"; + cuda2hipRename["cudaMemcpyDefault"] = "hipMemcpyDefault"; + cuda2hipRename["cudaMemcpyToSymbol"] = "hipMemcpyToSymbol"; + cuda2hipRename["cudaMemset"] = "hipMemset"; + cuda2hipRename["cudaMemsetAsync"] = "hipMemsetAsync"; + cuda2hipRename["cudaMemcpyAsync"] = "hipMemcpyAsync"; + cuda2hipRename["cudaMemGetInfo"] = "hipMemGetInfo"; + cuda2hipRename["cudaMemcpyKind"] = "hipMemcpyKind"; + + // Memory management : + cuda2hipRename["cudaMalloc"] = "hipMalloc"; + cuda2hipRename["cudaMallocHost"] = "hipMallocHost"; + cuda2hipRename["cudaFree"] = "hipFree"; + cuda2hipRename["cudaFreeHost"] = "hipFreeHost"; + + // Coordinate Indexing and Dimensions: + cuda2hipRename["threadIdx.x"] = "hipThreadIdx_x"; + cuda2hipRename["threadIdx.y"] = "hipThreadIdx_y"; + cuda2hipRename["threadIdx.z"] = "hipThreadIdx_z"; + + cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; + cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; + cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; + + cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; + cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; + cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; + + cuda2hipRename["gridDim.x"] = "hipGridDim_x"; + cuda2hipRename["gridDim.y"] = "hipGridDim_y"; + cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + + cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; + cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; + cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; + + cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; + cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; + cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; + + cuda2hipRename["gridDim.x"] = "hipGridDim_x"; + cuda2hipRename["gridDim.y"] = "hipGridDim_y"; + cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + + + cuda2hipRename["warpSize"] = "hipWarpSize"; + + // Events + cuda2hipRename["cudaEvent_t"] = "hipEvent_t"; + cuda2hipRename["cudaEventCreate"] = "hipEventCreate"; + cuda2hipRename["cudaEventCreateWithFlags"] = "hipEventCreateWithFlags"; + cuda2hipRename["cudaEventDestroy"] = "hipEventDestroy"; + cuda2hipRename["cudaEventRecord"] = "hipEventRecord"; + cuda2hipRename["cudaEventElapsedTime"] = "hipEventElapsedTime"; + cuda2hipRename["cudaEventSynchronize"] = "hipEventSynchronize"; + + // Streams + cuda2hipRename["cudaStream_t"] = "hipStream_t"; + cuda2hipRename["cudaStreamCreate"] = "hipStreamCreate"; + cuda2hipRename["cudaStreamCreateWithFlags"] = "hipStreamCreateWithFlags"; + cuda2hipRename["cudaStreamDestroy"] = "hipStreamDestroy"; + cuda2hipRename["cudaStreamWaitEvent"] = "hipStreamWaitEven"; + cuda2hipRename["cudaStreamSynchronize"] = "hipStreamSynchronize"; + cuda2hipRename["cudaStreamDefault"] = "hipStreamDefault"; + cuda2hipRename["cudaStreamNonBlocking"] = "hipStreamNonBlocking"; + + // Other synchronization + cuda2hipRename["cudaDeviceSynchronize"] = "hipDeviceSynchronize"; + cuda2hipRename["cudaThreadSynchronize"] = "hipDeviceSynchronize"; // translate deprecated cudaThreadSynchronize + cuda2hipRename["cudaDeviceReset"] = "hipDeviceReset"; + cuda2hipRename["cudaThreadExit"] = "hipDeviceReset"; // translate deprecated cudaThreadExit + cuda2hipRename["cudaSetDevice"] = "hipSetDevice"; + cuda2hipRename["cudaGetDevice"] = "hipGetDevice"; + + // Device + cuda2hipRename["cudaDeviceProp"] = "hipDeviceProp_t"; + cuda2hipRename["cudaGetDeviceProperties"] = "hipDeviceGetProperties"; + + // Cache config + cuda2hipRename["cudaDeviceSetCacheConfig"] = "hipDeviceSetCacheConfig"; + cuda2hipRename["cudaThreadSetCacheConfig"] = "hipDeviceSetCacheConfig"; // translate deprecated + cuda2hipRename["cudaDeviceGetCacheConfig"] = "hipDeviceGetCacheConfig"; + cuda2hipRename["cudaThreadGetCacheConfig"] = "hipDeviceGetCacheConfig"; // translate deprecated + cuda2hipRename["cudaFuncCache"] = "hipFuncCache"; + cuda2hipRename["cudaFuncCachePreferNone"] = "hipFuncCachePreferNone"; + cuda2hipRename["cudaFuncCachePreferShared"] = "hipFuncCachePreferShared"; + cuda2hipRename["cudaFuncCachePreferL1"] = "hipFuncCachePreferL1"; + cuda2hipRename["cudaFuncCachePreferEqual"] = "hipFuncCachePreferEqual"; + // function + cuda2hipRename["cudaFuncSetCacheConfig"] = "hipFuncSetCacheConfig"; + + cuda2hipRename["cudaDriverGetVersion"] = "hipDriverGetVersion"; + + // Peer2Peer + cuda2hipRename["cudaDeviceCanAccessPeer"] = "hipDeviceCanAccessPeer"; + cuda2hipRename["cudaDeviceDisablePeerAccess"] = "hipDeviceDisablePeerAccess"; + cuda2hipRename["cudaDeviceEnablePeerAccess"] = "hipDeviceEnablePeerAccess"; + cuda2hipRename["cudaMemcpyPeerAsync"] = "hipMemcpyPeerAsync"; + cuda2hipRename["cudaMemcpyPeer"] = "hipMemcpyPeer"; + + // Shared mem: + cuda2hipRename["cudaDeviceSetSharedMemConfig"] = "hipDeviceSetSharedMemConfig"; + cuda2hipRename["cudaThreadSetSharedMemConfig"] = "hipDeviceSetSharedMemConfig"; // translate deprecated + cuda2hipRename["cudaDeviceGetSharedMemConfig"] = "hipDeviceGetSharedMemConfig"; + cuda2hipRename["cudaThreadGetSharedMemConfig"] = "hipDeviceGetSharedMemConfig"; // translate deprecated + cuda2hipRename["cudaSharedMemConfig"] = "hipSharedMemConfig"; + cuda2hipRename["cudaSharedMemBankSizeDefault"] = "hipSharedMemBankSizeDefault"; + cuda2hipRename["cudaSharedMemBankSizeFourByte"] = "hipSharedMemBankSizeFourByte"; + cuda2hipRename["cudaSharedMemBankSizeEightByte"] = "hipSharedMemBankSizeEightByte"; + + cuda2hipRename["cudaGetDeviceCount"] = "hipGetDeviceCount"; + + // Profiler + //cuda2hipRename["cudaProfilerInitialize"] = "hipProfilerInitialize"; // see if these are called anywhere. + cuda2hipRename["cudaProfilerStart"] = "hipProfilerStart"; + cuda2hipRename["cudaProfilerStop"] = "hipProfilerStop"; + + cuda2hipRename["cudaChannelFormatDesc"] = "hipChannelFormatDesc"; + cuda2hipRename["cudaFilterModePoint"] = "hipFilterModePoint"; + cuda2hipRename["cudaReadModeElementType"] = "hipReadModeElementType"; + + cuda2hipRename["cudaCreateChannelDesc"] = "hipCreateChannelDesc"; + cuda2hipRename["cudaBindTexture"] = "hipBindTexture"; + cuda2hipRename["cudaUnbindTexture"] = "hipUnbindTexture"; + } + DenseMap cuda2hipRename; + }; + + struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { + HipifyPPCallbacks(Replacements * R) + : SeenEnd(false), _sm(nullptr), Replace(R) + { + } + + virtual bool handleBeginSource(CompilerInstance &CI, StringRef Filename) override + { + Preprocessor &PP = CI.getPreprocessor(); + SourceManager & SM = CI.getSourceManager(); + setSourceManager(&SM); + PP.addPPCallbacks(std::unique_ptr(this)); + PP.Retain(); + return true; + } + + virtual void InclusionDirective( + SourceLocation hash_loc, + const Token &include_token, + StringRef file_name, + bool is_angled, + CharSourceRange filename_range, + const FileEntry *file, + StringRef search_path, + StringRef relative_path, + const Module *imported) override + { + if (_sm->isWrittenInMainFile(hash_loc)) { + if (is_angled) { + if (N.cuda2hipRename.count(file_name)) { + std::string repName = N.cuda2hipRename[file_name]; + llvm::errs() << "\nInclude file found: " << file_name << "\n"; + llvm::errs() << "\nSourceLocation:"; filename_range.getBegin().dump(*_sm); + llvm::errs() << "\nWill be replaced with " << repName << "\n"; + SourceLocation sl = filename_range.getBegin(); + SourceLocation sle = filename_range.getEnd(); + const char* B = _sm->getCharacterData(sl); + const char* E = _sm->getCharacterData(sle); + repName = "<" + repName + ">"; + Replacement Rep(*_sm, sl, E - B, repName); + Replace->insert(Rep); + } + } + } + } + + virtual void MacroDefined(const Token &MacroNameTok, + const MacroDirective *MD) override + { + if (_sm->isWrittenInMainFile(MD->getLocation()) && + MD->getKind() == MacroDirective::MD_Define) + { + for (auto T : MD->getMacroInfo()->tokens()) + { + if (T.isAnyIdentifier()) { + StringRef name = T.getIdentifierInfo()->getName(); + if (N.cuda2hipRename.count(name)) { + StringRef repName = N.cuda2hipRename[name]; + llvm::errs() << "\nIdentifier " << name + << " found in definition of macro " << MacroNameTok.getIdentifierInfo()->getName() << "\n"; + llvm::errs() << "\nwill be replaced with: " << repName << "\n"; + SourceLocation sl = T.getLocation(); + llvm::errs() << "\nSourceLocation: ";sl.dump(*_sm); + llvm::errs() << "\n"; + Replacement Rep(*_sm, sl, name.size(), repName); + Replace->insert(Rep); + } + } + } + } + } + + void EndOfMainFile() override + { + + } + + bool SeenEnd; + void setSourceManager(SourceManager * sm) { _sm = sm; } + + private: + + SourceManager * _sm; + Replacements * Replace; + struct hipName N; + }; + +class Cuda2HipCallback : public MatchFinder::MatchCallback { + public: + Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} + + void run(const MatchFinder::MatchResult &Result) override { + + SourceManager * SM = Result.SourceManager; + + if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) + { + const FunctionDecl * funcDcl = call->getDirectCallee(); + std::string name = funcDcl->getDeclName().getAsString(); + if (N.cuda2hipRename.count(name)) { + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = call->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } + } + + if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) + { + LangOptions DefaultLangOptions; + + const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); + + const ParmVarDecl * pvdFirst = kernelDecl->getParamDecl(0); + const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); + SourceLocation kernelArgListStart(pvdFirst->getLocStart()); + SourceLocation kernelArgListEnd(pvdLast->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); + size_t replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); + std::string outs(SM->getCharacterData(kernelArgListStart), replacementLength); + llvm::outs() << "initial paramlist: " << outs.c_str() << "\n"; + outs = "hipLaunchParm lp, " + outs; + llvm::outs() << "new paramlist: " << outs.c_str() << "\n"; + Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, outs); + Replace->insert(Rep0); + + + std::string name = kernelDecl->getDeclName().getAsString(); + std::string repName = "hipLaunchKernel(HIP_KERNEL_NAME(" + name + "), "; + + + const CallExpr * config = launchKernel->getConfig(); + llvm::outs() << "\nKernel config arguments:\n"; + for (unsigned argno = 0; argno < config->getNumArgs(); argno++) + { + const Expr * arg = config->getArg(argno); + if (!isa(arg)) { + std::string typeCtor = ""; + const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); + + SourceLocation sl(arg->getLocStart()); + SourceLocation el(arg->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + llvm::outs() << "args[ " << argno << "]" << outs.c_str() << " <" << pvd->getType().getAsString() << ">\n"; + if (pvd->getType().getAsString().compare("dim3") == 0) + repName += " dim3(" + outs + "),"; + else + repName += " " + outs + ","; + } else + repName += " 0,"; + } + + for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) + { + const Expr * arg = launchKernel->getArg(argno); + SourceLocation sl(arg->getLocStart()); + SourceLocation el(arg->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + llvm::outs() << outs.c_str() << "\n"; + repName += " " + outs + ","; + } + repName.pop_back(); + repName += ")"; + size_t length = SM->getCharacterData(clang::Lexer::getLocForEndOfToken(launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - + SM->getCharacterData(launchKernel->getLocStart()); + Replacement Rep(*SM, launchKernel->getLocStart(), length, repName); + Replace->insert(Rep); + } + + if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) + { + if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { + if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { + std::string name = declRef->getDecl()->getNameAsString(); + std::string memberName = threadIdx->getMemberDecl()->getNameAsString(); + size_t pos = memberName.find_first_not_of("__fetch_builtin_"); + memberName = memberName.substr(pos, memberName.length() - pos); + name += "." + memberName; + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = threadIdx->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } + } + } + + if (const DeclRefExpr * cudaEnumConstant = Result.Nodes.getNodeAs("cudaEnumConstant")) + { + std::string name = cudaEnumConstant->getDecl()->getNameAsString(); + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = cudaEnumConstant->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } + + if (const VarDecl * cudaStructVar = Result.Nodes.getNodeAs("cudaStructVar")) + { + std::string name = + cudaStructVar->getType()->getAsStructureType()->getDecl()->getNameAsString(); + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = cudaStructVar->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } + } + + private: + Replacements *Replace; + struct hipName N; +}; + +} // end anonymous namespace + +// Set up the command line options +static cl::extrahelp CommonHelp(CommonOptionsParser::HelpMessage); +static cl::OptionCategory ToolTemplateCategory("CUDA to HIP source translator options"); + +int main(int argc, const char **argv) { + + llvm::sys::PrintStackTraceOnErrorSignal(); + + int Result; + + CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory); + std::vector savedSources; + for (auto I : OptionsParser.getSourcePathList()) + { + size_t pos = I.find(".cu"); + if (pos != std::string::npos) + { + std::string dst = I.substr(0, pos) + ".hip.cu"; + std::ifstream source(I, std::ios::binary); + std::ofstream dest(dst, std::ios::binary); + dest << source.rdbuf(); + source.close(); + dest.close(); + savedSources.push_back(dst); + } + } + + RefactoringTool Tool(OptionsParser.getCompilations(), savedSources); + ast_matchers::MatchFinder Finder; + Cuda2HipCallback Callback(&Tool.getReplacements()); + HipifyPPCallbacks PPCallbacks(&Tool.getReplacements()); + Finder.addMatcher(callExpr(isExpansionInMainFile(), callee(functionDecl(matchesName("cuda.*")))).bind("cudaCall"), &Callback); + Finder.addMatcher(cudaKernelCallExpr().bind("cudaLaunchKernel"), &Callback); + Finder.addMatcher(memberExpr(isExpansionInMainFile(), hasObjectExpression(hasType(cxxRecordDecl(matchesName("__cuda_builtin_"))))).bind("cudaBuiltin"), &Callback); + Finder.addMatcher(declRefExpr(isExpansionInMainFile(), to(enumConstantDecl(matchesName("cuda.*")))).bind("cudaEnumConstant"), &Callback); + Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); + + auto action = newFrontendActionFactory(&Finder, &PPCallbacks); + + std::vector compilationStages; + compilationStages.push_back("--cuda-host-only"); + compilationStages.push_back("--cuda-device-only"); + + for (auto Stage : compilationStages) + { + Tool.appendArgumentsAdjuster(combineAdjusters( + getInsertArgumentAdjuster(Stage, ArgumentInsertPosition::BEGIN), + getClangSyntaxOnlyAdjuster())); + + Result = Tool.run(action.get()); + + Tool.clearArgumentsAdjusters(); + } + + LangOptions DefaultLangOptions; + IntrusiveRefCntPtr DiagOpts = new DiagnosticOptions(); + TextDiagnosticPrinter DiagnosticPrinter(llvm::errs(), &*DiagOpts); + DiagnosticsEngine Diagnostics( + IntrusiveRefCntPtr(new DiagnosticIDs()), + &*DiagOpts, &DiagnosticPrinter, false); + SourceManager Sources(Diagnostics, Tool.getFiles()); + + llvm::outs() << "Replacements collected by the tool:\n"; + for (auto &r : Tool.getReplacements()) { + llvm::outs() << r.toString() << "\n"; + } + + Rewriter Rewrite(Sources, DefaultLangOptions); + + if (!Tool.applyAllReplacements(Rewrite)) { + llvm::errs() << "Skipped some replacements.\n"; + } + + Result = Rewrite.overwriteChangedFiles(); + + + for (auto I : savedSources) + { + size_t pos = I.find(".cu"); + if (pos != std::string::npos) + { + rename(I.c_str(), I.substr(0, pos).c_str()); + } + } + return Result; +} From bae0f00e69d5efa24e32e33b8db5c81906ae5c81 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Thu, 11 Feb 2016 15:27:00 +0300 Subject: [PATCH 03/56] adding ability to build in llvm source tree, updated README --- hipamd/CMakeLists.txt | 39 ++++++++++++++++++++++++++------------- hipamd/README.md | 36 +++++++++++++++++++++++++++++++----- 2 files changed, 57 insertions(+), 18 deletions(-) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 6d727c70be..56845f1b6e 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -1,18 +1,25 @@ -cmake_minimum_required(VERSION 2.8.8) +if(${HIPIFY_STANDLONE}) + cmake_minimum_required(VERSION 2.8.8) -project(hipify) + project(hipify) -find_package(LLVM REQUIRED PATHS ${LLVM_DIR} NO_DEFAULT_PATH) + find_package(LLVM REQUIRED PATHS ${LLVM_DIR} NO_DEFAULT_PATH) -message(STATUS "Found LLVM ${LLVM_PACKAGE_VERSION}") -message(STATUS "Using LLVMConfig.cmake in: ${LLVM_DIR}") + message(STATUS "Found LLVM ${LLVM_PACKAGE_VERSION}") + message(STATUS "Using LLVMConfig.cmake in: ${LLVM_DIR}") -include_directories(${LLVM_INCLUDE_DIRS}) -link_directories(${LLVM_LIBRARY_DIRS}) -add_definitions(${LLVM_DEFINITIONS}) + include_directories(${LLVM_INCLUDE_DIRS}) + link_directories(${LLVM_LIBRARY_DIRS}) + add_definitions(${LLVM_DEFINITIONS}) + add_executable( hipify src/Cuda2Hip.cpp ) +else() + set(LLVM_LINK_COMPONENTS + Option + Support + ) + add_clang_executable(hipify src/Cuda2Hip.cpp) +endif() -# Now build our tools -add_executable(hipify src/Cuda2Hip.cpp) # Link against LLVM and CLANG tools libraries target_link_libraries(hipify @@ -37,6 +44,12 @@ target_link_libraries(hipify LLVMOption LLVMCore) -set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_CFLAGS}") -set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS}") -set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -std=c++11 -pthread -D __STDC_LIMIT_MACROS -D __STDC_CONSTANT_MACROS -D __STDC_FORMAT_MACROS -fno-rtti -fvisibility-inlines-hidden") +if(${HIPIFY_STANDLONE}) + set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_CFLAGS}") + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS}") + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -std=c++11 -pthread -fno-rtti -fvisibility-inlines-hidden") +else() + install(TARGETS hipify + RUNTIME DESTINATION bin + COMPONENT clang-extras) +endif() diff --git a/hipamd/README.md b/hipamd/README.md index a813325e65..08b3a5eb5f 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -1,10 +1,36 @@ # HIPIFY The CLANG-based HIPIFY tool - translates CUDA to [HIP](https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP/blob/master/README.md) -# How to Build -- Get LLVM and CLANG sources and build CLANG, then install it to a **LLVM_INSTALL_PATH** folder -- make build dir for hipify and run the folloing commands there: +# How to Build *standalone* tool +- Get LLVM and CLANG sources, build them and install to a **LLVM_INSTALL_PATH** folder +- mkdir for hipify, run cmake there and build the tool: ``` -> cmake -DLLVM_DIR="LLVM_INSTALL_PATH" path_to_hipify_src -> make +git clone http://llvm.org/git/llvm.git llvm +git clone http://llvm.org/git/clang.git llvm/tools/clang + +mkdir llvm_build && cd llvm_build +cmake -DCMAKE_INSTALL_PREFIX="LLVM_INSTALL_PATH" -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm +make && make install + +git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git path_to_hipify_src +mkdir path_to_hipify_src/build && cd path_to_hipify_src/build +cmake -DLLVM_DIR="LLVM_INSTALL_PATH" -DHIPIFY_STANDLONE=1 .. +make ``` + +# How to Build tool *in llvm source tree* +- get LLVM, CLANG and clang-tools-extra sources +- put hipify folder into llvm/tools/clang/tools/extra, add it to llvm/tools/clang/tools/extra/CMakeLists.txt +- run cmake and build tool +``` +git clone http://llvm.org/git/llvm.git llvm +git clone http://llvm.org/git/clang.git llvm/tools/clang +git clone http://llvm.org/git/clang-tools-extra.git llvm/tools/clang/tools/extra +git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git llvm/tools/clang/tools/extra/hipify +echo "add_subdirectory(hipify)" >> llvm/tools/clang/tools/extra/CMakeLists.txt + +mkdir llvm_build && cd llvm_build +cmake -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm +make -C tools/clang/tools/extra/hipify +``` + From 5cd248c55f8cc37519abf921444322bb52ad57cb Mon Sep 17 00:00:00 2001 From: atimofee Date: Wed, 17 Feb 2016 18:34:58 +0300 Subject: [PATCH 04/56] Hipify tool in it current state --- hipamd/src/Cuda2Hip.cpp | 177 ++++++++++++++++++++++++---------------- 1 file changed, 105 insertions(+), 72 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index c4c8f58810..fe3f360dce 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -1,29 +1,39 @@ -/* -Copyright (c) 2015-2016 Advanced Micro Devices, Inc. All rights reserved. +//===---- tools/extra/ToolTemplate.cpp - Template for refactoring tool ----===// +// +// The LLVM Compiler Infrastructure +// +// This file is distributed under the University of Illinois Open Source +// License. See LICENSE.TXT for details. +// +//===----------------------------------------------------------------------===// +// +// This file implements an empty refactoring tool using the clang tooling. +// The goal is to lower the "barrier to entry" for writing refactoring tools. +// +// Usage: +// tool-template ... +// +// Where is a CMake build directory in which a file named +// compile_commands.json exists (enable -DCMAKE_EXPORT_COMPILE_COMMANDS in +// CMake to get this output). +// +// ... specify the paths of files in the CMake source tree. This path +// is looked up in the compile command database. If the path of a file is +// absolute, it needs to point into CMake's source tree. If the path is +// relative, the current working directory needs to be in the CMake source +// tree and the file must be in a subdirectory of the current working +// directory. "./" prefixes in the relative files will be automatically +// removed, but the rest of a relative path must be a suffix of a path in +// the compile command line database. +// +// For example, to use tool-template on all files in a subtree of the +// source tree, use: +// +// /path/in/subtree $ find . -name '*.cpp'| +// xargs tool-template /path/to/build +// +//===----------------------------------------------------------------------===// -Permission is hereby granted, free of charge, to any person obtaining a copy -of this software and associated documentation files (the "Software"), to deal -in the Software without restriction, including without limitation the rights -to use, copy, modify, merge, publish, distribute, sublicense, and/or sell -copies of the Software, and to permit persons to whom the Software is -furnished to do so, subject to the following conditions: - -The above copyright notice and this permission notice shall be included in -all copies or substantial portions of the Software. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, -OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN -THE SOFTWARE. -*/ -/** - * @file Cuda2Hip.cpp - * - * This file is compiled and linked into clang based hipify tool. - */ #include "clang/ASTMatchers/ASTMatchers.h" #include "clang/ASTMatchers/ASTMatchFinder.h" #include "clang/Basic/SourceManager.h" @@ -65,7 +75,7 @@ namespace { // Error codes and return types: cuda2hipRename["cudaError_t"] = "hipError_t"; - cuda2hipRename["cudaError"] = "hipError_t"; + cuda2hipRename["cudaError"] = "hipError"; cuda2hipRename["cudaSuccess"] = "hipSuccess"; cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; @@ -138,7 +148,7 @@ namespace { cuda2hipRename["warpSize"] = "hipWarpSize"; - // Events + // Events cuda2hipRename["cudaEvent_t"] = "hipEvent_t"; cuda2hipRename["cudaEventCreate"] = "hipEventCreate"; cuda2hipRename["cudaEventCreateWithFlags"] = "hipEventCreateWithFlags"; @@ -157,7 +167,7 @@ namespace { cuda2hipRename["cudaStreamDefault"] = "hipStreamDefault"; cuda2hipRename["cudaStreamNonBlocking"] = "hipStreamNonBlocking"; - // Other synchronization + // Other synchronization cuda2hipRename["cudaDeviceSynchronize"] = "hipDeviceSynchronize"; cuda2hipRename["cudaThreadSynchronize"] = "hipDeviceSynchronize"; // translate deprecated cudaThreadSynchronize cuda2hipRename["cudaDeviceReset"] = "hipDeviceReset"; @@ -165,7 +175,7 @@ namespace { cuda2hipRename["cudaSetDevice"] = "hipSetDevice"; cuda2hipRename["cudaGetDevice"] = "hipGetDevice"; - // Device + // Device cuda2hipRename["cudaDeviceProp"] = "hipDeviceProp_t"; cuda2hipRename["cudaGetDeviceProperties"] = "hipDeviceGetProperties"; @@ -219,22 +229,22 @@ namespace { DenseMap cuda2hipRename; }; - struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { - HipifyPPCallbacks(Replacements * R) - : SeenEnd(false), _sm(nullptr), Replace(R) - { - } - - virtual bool handleBeginSource(CompilerInstance &CI, StringRef Filename) override - { - Preprocessor &PP = CI.getPreprocessor(); - SourceManager & SM = CI.getSourceManager(); - setSourceManager(&SM); - PP.addPPCallbacks(std::unique_ptr(this)); - PP.Retain(); - return true; - } - + struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { + HipifyPPCallbacks(Replacements * R) + : SeenEnd(false), _sm(nullptr), Replace(R) + { + } + + virtual bool handleBeginSource(CompilerInstance &CI, StringRef Filename) override + { + Preprocessor &PP = CI.getPreprocessor(); + SourceManager & SM = CI.getSourceManager(); + setSourceManager(&SM); + PP.addPPCallbacks(std::unique_ptr(this)); + PP.Retain(); + return true; + } + virtual void InclusionDirective( SourceLocation hash_loc, const Token &include_token, @@ -255,8 +265,8 @@ namespace { llvm::errs() << "\nWill be replaced with " << repName << "\n"; SourceLocation sl = filename_range.getBegin(); SourceLocation sle = filename_range.getEnd(); - const char* B = _sm->getCharacterData(sl); - const char* E = _sm->getCharacterData(sle); + const char* B = _sm->getCharacterData(sl); + const char* E = _sm->getCharacterData(sle); repName = "<" + repName + ">"; Replacement Rep(*_sm, sl, E - B, repName); Replace->insert(Rep); @@ -290,22 +300,22 @@ namespace { } } } - - void EndOfMainFile() override - { - - } - - bool SeenEnd; - void setSourceManager(SourceManager * sm) { _sm = sm; } - - private: - - SourceManager * _sm; - Replacements * Replace; - struct hipName N; - }; - + + void EndOfMainFile() override + { + + } + + bool SeenEnd; + void setSourceManager(SourceManager * sm) { _sm = sm; } + + private: + + SourceManager * _sm; + Replacements * Replace; + struct hipName N; + }; + class Cuda2HipCallback : public MatchFinder::MatchCallback { public: Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} @@ -349,7 +359,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { std::string name = kernelDecl->getDeclName().getAsString(); std::string repName = "hipLaunchKernel(HIP_KERNEL_NAME(" + name + "), "; - + const CallExpr * config = launchKernel->getConfig(); llvm::outs() << "\nKernel config arguments:\n"; @@ -359,7 +369,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (!isa(arg)) { std::string typeCtor = ""; const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); - + SourceLocation sl(arg->getLocStart()); SourceLocation el(arg->getLocEnd()); SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); @@ -372,7 +382,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { } else repName += " 0,"; } - + for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) { const Expr * arg = launchKernel->getArg(argno); @@ -409,11 +419,21 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { } } - if (const DeclRefExpr * cudaEnumConstant = Result.Nodes.getNodeAs("cudaEnumConstant")) + if (const DeclRefExpr * cudaEnumConstantRef = Result.Nodes.getNodeAs("cudaEnumConstantRef")) { - std::string name = cudaEnumConstant->getDecl()->getNameAsString(); + std::string name = cudaEnumConstantRef->getDecl()->getNameAsString(); std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = cudaEnumConstant->getLocStart(); + SourceLocation sl = cudaEnumConstantRef->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } + + if (const VarDecl * cudaEnumConstantDecl = Result.Nodes.getNodeAs("cudaEnumConstantDecl")) + { + std::string name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = cudaEnumConstantDecl->getLocStart(); Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); Replace->insert(Rep); @@ -429,6 +449,17 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); Replace->insert(Rep); } + + if (const ParmVarDecl * cudaParamDecl = Result.Nodes.getNodeAs("cudaParamDecl")) + { + QualType QT = cudaParamDecl->getOriginalType(); + std::string name = QT.getAsString(); + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = cudaParamDecl->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } } private: @@ -447,7 +478,7 @@ int main(int argc, const char **argv) { llvm::sys::PrintStackTraceOnErrorSignal(); int Result; - + CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory); std::vector savedSources; for (auto I : OptionsParser.getSourcePathList()) @@ -472,8 +503,10 @@ int main(int argc, const char **argv) { Finder.addMatcher(callExpr(isExpansionInMainFile(), callee(functionDecl(matchesName("cuda.*")))).bind("cudaCall"), &Callback); Finder.addMatcher(cudaKernelCallExpr().bind("cudaLaunchKernel"), &Callback); Finder.addMatcher(memberExpr(isExpansionInMainFile(), hasObjectExpression(hasType(cxxRecordDecl(matchesName("__cuda_builtin_"))))).bind("cudaBuiltin"), &Callback); - Finder.addMatcher(declRefExpr(isExpansionInMainFile(), to(enumConstantDecl(matchesName("cuda.*")))).bind("cudaEnumConstant"), &Callback); + Finder.addMatcher(declRefExpr(isExpansionInMainFile(), to(enumConstantDecl(matchesName("cuda.*")))).bind("cudaEnumConstantRef"), &Callback); + Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))).bind("cudaEnumConstantDecl"), &Callback); Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); + Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); auto action = newFrontendActionFactory(&Finder, &PPCallbacks); @@ -491,7 +524,7 @@ int main(int argc, const char **argv) { Tool.clearArgumentsAdjusters(); } - + LangOptions DefaultLangOptions; IntrusiveRefCntPtr DiagOpts = new DiagnosticOptions(); TextDiagnosticPrinter DiagnosticPrinter(llvm::errs(), &*DiagOpts); From cdcb45d9f272a69e080439cc1575468993376c37 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Wed, 17 Feb 2016 19:05:18 +0300 Subject: [PATCH 05/56] Adding lit tests --- hipamd/CMakeLists.txt | 9 +++++-- hipamd/README.md | 13 ++++++++- hipamd/test/CMakeLists.txt | 27 +++++++++++++++++++ hipamd/test/axpy.cu | 43 +++++++++++++++++++++++++++++ hipamd/test/lit.cfg | 54 +++++++++++++++++++++++++++++++++++++ hipamd/test/lit.site.cfg.in | 15 +++++++++++ 6 files changed, 158 insertions(+), 3 deletions(-) create mode 100644 hipamd/test/CMakeLists.txt create mode 100644 hipamd/test/axpy.cu create mode 100644 hipamd/test/lit.cfg create mode 100644 hipamd/test/lit.site.cfg.in diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 56845f1b6e..8915cc4714 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -1,17 +1,21 @@ if(${HIPIFY_STANDLONE}) cmake_minimum_required(VERSION 2.8.8) - + project(hipify) find_package(LLVM REQUIRED PATHS ${LLVM_DIR} NO_DEFAULT_PATH) + list(APPEND CMAKE_MODULE_PATH ${LLVM_CMAKE_DIR}) + include(AddLLVM) + message(STATUS "Found LLVM ${LLVM_PACKAGE_VERSION}") message(STATUS "Using LLVMConfig.cmake in: ${LLVM_DIR}") include_directories(${LLVM_INCLUDE_DIRS}) link_directories(${LLVM_LIBRARY_DIRS}) add_definitions(${LLVM_DEFINITIONS}) - add_executable( hipify src/Cuda2Hip.cpp ) + add_llvm_executable( hipify src/Cuda2Hip.cpp ) + else() set(LLVM_LINK_COMPONENTS Option @@ -48,6 +52,7 @@ if(${HIPIFY_STANDLONE}) set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_CFLAGS}") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS}") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -std=c++11 -pthread -fno-rtti -fvisibility-inlines-hidden") + add_subdirectory(test) else() install(TARGETS hipify RUNTIME DESTINATION bin diff --git a/hipamd/README.md b/hipamd/README.md index 08b3a5eb5f..a3725394ad 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -9,7 +9,7 @@ git clone http://llvm.org/git/llvm.git llvm git clone http://llvm.org/git/clang.git llvm/tools/clang mkdir llvm_build && cd llvm_build -cmake -DCMAKE_INSTALL_PREFIX="LLVM_INSTALL_PATH" -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm +cmake -DCMAKE_INSTALL_PREFIX="LLVM_INSTALL_PATH" -DLLVM_INSTALL_UTILS=ON -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm make && make install git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git path_to_hipify_src @@ -34,3 +34,14 @@ cmake -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm make -C tools/clang/tools/extra/hipify ``` +# How to run tests (for *standalone* tool only) +- install Python and add python-setuptools +- install lit python script +- make sure that FileCheck util is installed to **LLVM_INSTALL_PATH/bin/FileCheck** +- run tests from path_to_hipify_src/build +``` +sudo apt-get install python python-setuptools +sudo easy_install lit +make -C path_to_hipify_src/build test +``` + diff --git a/hipamd/test/CMakeLists.txt b/hipamd/test/CMakeLists.txt new file mode 100644 index 0000000000..4f74091b0b --- /dev/null +++ b/hipamd/test/CMakeLists.txt @@ -0,0 +1,27 @@ +set(Python_ADDITIONAL_VERSIONS 2.7) +include(FindPythonInterp) +if( NOT PYTHONINTERP_FOUND ) + message(FATAL_ERROR + "Unable to find Python interpreter, required for builds and testing\n\n" + "Please install Python or specify the PYTHON_EXECUTABLE CMake variable.") +endif() + +set(BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR} ) + +configure_file( + ${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.in + ${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg + @ONLY) + +add_lit_testsuite(check-hipify "Running HIPify regression tests" + ${CMAKE_CURRENT_SOURCE_DIR} + PARAMS site_config=${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg + DEPENDS hipify + ) + +add_custom_target(check) +add_dependencies(check check-hipify) +add_custom_target(test) +add_dependencies(test check-hipify) +set_target_properties(check PROPERTIES FOLDER "Tests") + diff --git a/hipamd/test/axpy.cu b/hipamd/test/axpy.cu new file mode 100644 index 0000000000..29d5493763 --- /dev/null +++ b/hipamd/test/axpy.cu @@ -0,0 +1,43 @@ +// RUN: hipify "%s" 2>&1 | FileCheck %s + +#include // for checkCudaErrors + +#include + +__global__ void axpy(float a, float* x, float* y) { + // CHECK: hipThreadIdx_x + y[threadIdx.x] = a * x[threadIdx.x]; +} + +int main(int argc, char* argv[]) { + const int kDataLen = 4; + + float a = 2.0f; + float host_x[kDataLen] = {1.0f, 2.0f, 3.0f, 4.0f}; + float host_y[kDataLen]; + + // Copy input data to device. + float* device_x; + float* device_y; + checkCudaErrors(cudaMalloc(&device_x, kDataLen * sizeof(float))); + checkCudaErrors(cudaMalloc(&device_y, kDataLen * sizeof(float))); + checkCudaErrors(cudaMemcpy(device_x, host_x, kDataLen * sizeof(float), + cudaMemcpyHostToDevice)); + + // Launch the kernel. + // CHECK: hipLaunchKernel(HIP_KERNEL_NAME + axpy<<<1, kDataLen>>>(a, device_x, device_y); + + // Copy output data to host. + checkCudaErrors(cudaDeviceSynchronize()); + checkCudaErrors(cudaMemcpy(host_y, device_y, kDataLen * sizeof(float), + cudaMemcpyDeviceToHost)); + + // Print the results. + for (int i = 0; i < kDataLen; ++i) { + std::cout << "y[" << i << "] = " << host_y[i] << "\n"; + } + + checkCudaErrors(cudaDeviceReset()); + return 0; +} diff --git a/hipamd/test/lit.cfg b/hipamd/test/lit.cfg new file mode 100644 index 0000000000..775cdbf0d4 --- /dev/null +++ b/hipamd/test/lit.cfg @@ -0,0 +1,54 @@ +# -*- Python -*- +import os +import platform +import re +import subprocess + +import lit.formats +import lit.util + +# Configuration file for the 'lit' test runner. + +# name: The name of this test suite. +config.name = 'hipify' + +# suffixes: CUDA source is only supported +config.suffixes = ['.cu'] + +# testFormat: The test format to use to interpret tests. +config.test_format = lit.formats.ShTest() + +# test_source_root: The root path where tests are located. +config.test_source_root = os.path.dirname(__file__) + +# test_exec_root: The path where tests are located (default is the test suite root). +#config.test_exec_root = config.test_source_root + +# target_triple: Used by ShTest and TclTest formats for XFAIL checks. +config.target_triple = '(unused)' + +# available_features: Used by ShTest and TclTest formats for REQUIRES checks. +config.available_features = [] + +site_cfg = lit_config.params.get('site_config', None) +lit_config.load_config(config, site_cfg) + +obj_root = getattr(config, 'obj_root', None) +if obj_root is not None: + config.test_exec_root = obj_root + +if obj_root is not None: + llvm_tools_dir = getattr(config, 'llvm_tools_dir', None) + if not llvm_tools_dir: + lit_config.fatal('No LLVM tools dir set!') + path = os.path.pathsep.join((llvm_tools_dir, config.environment['PATH'])) + config.environment['PATH'] = path + +tool_name = "FileCheck" +tool_path = lit.util.which(tool_name, llvm_tools_dir) +if not tool_path: + # Warn, but still provide a substitution. + lit_config.note('Did not find ' + tool_name + ' in ' + llvm_tools_dir) + tool_path = llvm_tools_dir + '/' + tool_name +config.substitutions.append((tool_name, tool_path)) + diff --git a/hipamd/test/lit.site.cfg.in b/hipamd/test/lit.site.cfg.in new file mode 100644 index 0000000000..6fc35440d4 --- /dev/null +++ b/hipamd/test/lit.site.cfg.in @@ -0,0 +1,15 @@ +import sys + +config.llvm_tools_dir = "@LLVM_TOOLS_BINARY_DIR@" +config.obj_root = "@CMAKE_CURRENT_BINARY_DIR@" + +# Support substitution of the tools and libs dirs with user parameters. This is +# used when we can't determine the tool dir at configuration time. +try: + config.llvm_tools_dir = config.llvm_tools_dir % lit_config.params + config.obj_root = config.obj_root % lit_config.params +except KeyError: + e = sys.exc_info()[1] + key, = e.args + lit_config.fatal("unable to find %r parameter, use '--param=%s=VALUE'" % (key,key)) + From 1f77fd5dcc76a8c87a3a1b4acd6b34d00d984638 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Thu, 18 Feb 2016 23:16:52 +0300 Subject: [PATCH 06/56] fix build bug with current clang/llvm --- hipamd/src/Cuda2Hip.cpp | 76 ++++++++++++++++++++--------------------- 1 file changed, 38 insertions(+), 38 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index fe3f360dce..f8cf938f32 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -229,22 +229,22 @@ namespace { DenseMap cuda2hipRename; }; - struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { - HipifyPPCallbacks(Replacements * R) - : SeenEnd(false), _sm(nullptr), Replace(R) - { - } - - virtual bool handleBeginSource(CompilerInstance &CI, StringRef Filename) override - { - Preprocessor &PP = CI.getPreprocessor(); - SourceManager & SM = CI.getSourceManager(); - setSourceManager(&SM); - PP.addPPCallbacks(std::unique_ptr(this)); - PP.Retain(); - return true; - } - + struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { + HipifyPPCallbacks(Replacements * R) + : SeenEnd(false), _sm(nullptr), Replace(R) + { + } + + virtual bool handleBeginSource(CompilerInstance &CI, StringRef Filename) override + { + Preprocessor &PP = CI.getPreprocessor(); + SourceManager & SM = CI.getSourceManager(); + setSourceManager(&SM); + PP.addPPCallbacks(std::unique_ptr(this)); + PP.Retain(); + return true; + } + virtual void InclusionDirective( SourceLocation hash_loc, const Token &include_token, @@ -254,7 +254,7 @@ namespace { const FileEntry *file, StringRef search_path, StringRef relative_path, - const Module *imported) override + const clang::Module *imported) override { if (_sm->isWrittenInMainFile(hash_loc)) { if (is_angled) { @@ -265,8 +265,8 @@ namespace { llvm::errs() << "\nWill be replaced with " << repName << "\n"; SourceLocation sl = filename_range.getBegin(); SourceLocation sle = filename_range.getEnd(); - const char* B = _sm->getCharacterData(sl); - const char* E = _sm->getCharacterData(sle); + const char* B = _sm->getCharacterData(sl); + const char* E = _sm->getCharacterData(sle); repName = "<" + repName + ">"; Replacement Rep(*_sm, sl, E - B, repName); Replace->insert(Rep); @@ -300,22 +300,22 @@ namespace { } } } - - void EndOfMainFile() override - { - - } - - bool SeenEnd; - void setSourceManager(SourceManager * sm) { _sm = sm; } - - private: - - SourceManager * _sm; - Replacements * Replace; - struct hipName N; - }; - + + void EndOfMainFile() override + { + + } + + bool SeenEnd; + void setSourceManager(SourceManager * sm) { _sm = sm; } + + private: + + SourceManager * _sm; + Replacements * Replace; + struct hipName N; + }; + class Cuda2HipCallback : public MatchFinder::MatchCallback { public: Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} @@ -452,8 +452,8 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (const ParmVarDecl * cudaParamDecl = Result.Nodes.getNodeAs("cudaParamDecl")) { - QualType QT = cudaParamDecl->getOriginalType(); - std::string name = QT.getAsString(); + QualType QT = cudaParamDecl->getOriginalType(); + std::string name = QT.getAsString(); std::string repName = N.cuda2hipRename[name]; SourceLocation sl = cudaParamDecl->getLocStart(); Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? @@ -506,7 +506,7 @@ int main(int argc, const char **argv) { Finder.addMatcher(declRefExpr(isExpansionInMainFile(), to(enumConstantDecl(matchesName("cuda.*")))).bind("cudaEnumConstantRef"), &Callback); Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))).bind("cudaEnumConstantDecl"), &Callback); Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); - Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); + Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); auto action = newFrontendActionFactory(&Finder, &PPCallbacks); From 88b4f2859fce2f12ef4a741b710fb5b8160890c1 Mon Sep 17 00:00:00 2001 From: atimofee Date: Fri, 19 Feb 2016 21:58:33 +0300 Subject: [PATCH 07/56] Added CUDA names replacement in string literals (i.e. error messages) --- hipamd/src/Cuda2Hip.cpp | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index fe3f360dce..ff6f0c9262 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -460,6 +460,21 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); Replace->insert(Rep); } + if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) + { + std::string s = stringLiteral->getString(); + std::string search("cuda"), replace("hip"); + size_t pos = 0; + while ((pos = s.find("cuda", pos)) != std::string::npos) { + llvm::outs() << "String Literal: " << s << "\n"; + s.replace(pos, search.length(), replace); + pos += replace.length(); + SourceLocation sl = stringLiteral->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, stringLiteral->getLength(), s); + Replace->insert(Rep); + } + } } private: @@ -507,6 +522,7 @@ int main(int argc, const char **argv) { Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))).bind("cudaEnumConstantDecl"), &Callback); Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); + Finder.addMatcher(stringLiteral().bind("stringLiteral"), &Callback); auto action = newFrontendActionFactory(&Finder, &PPCallbacks); From 8bf31a49c8f805111f54d3ea69785f37fd9781f7 Mon Sep 17 00:00:00 2001 From: atimofee Date: Wed, 24 Feb 2016 17:42:02 +0300 Subject: [PATCH 08/56] CUDA names in string literals replacment added --- hipamd/src/Cuda2Hip.cpp | 37 ++++++++++++++++++++++++------------- 1 file changed, 24 insertions(+), 13 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index ff6f0c9262..6a0b6fa42c 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -254,7 +254,7 @@ namespace { const FileEntry *file, StringRef search_path, StringRef relative_path, - const Module *imported) override + const clang::Module *imported) override { if (_sm->isWrittenInMainFile(hash_loc)) { if (is_angled) { @@ -462,18 +462,29 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { } if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) { - std::string s = stringLiteral->getString(); - std::string search("cuda"), replace("hip"); - size_t pos = 0; - while ((pos = s.find("cuda", pos)) != std::string::npos) { - llvm::outs() << "String Literal: " << s << "\n"; - s.replace(pos, search.length(), replace); - pos += replace.length(); - SourceLocation sl = stringLiteral->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, stringLiteral->getLength(), s); - Replace->insert(Rep); - } + StringRef s = stringLiteral->getString(); + + std::pair split = s.split("cuda"); + StringRef cuda = split.second; + while (!cuda.empty()) { + size_t byteNum = split.first.size(); + cuda = cuda.data() - 4; + std::pair name_pair = cuda.split(' '); + StringRef name = name_pair.first; + llvm::outs() << "\nToken: <" << name << "> found in string literal " << s << "\n"; + StringRef repName = N.cuda2hipRename[name]; + if (!repName.empty()) + { + llvm::outs() << "\nWill be replaced with: <" << repName << ">\n"; + SourceLocation sl = stringLiteral->getLocationOfByte(byteNum, *SM, + Result.Context->getLangOpts(), Result.Context->getTargetInfo()); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replace->insert(Rep); + } + split = name_pair.second.split("cuda"); + cuda = split.second; + } } } From ac30cbfe650e4fd09c684097a0ae3fc6c4e91052 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Wed, 24 Feb 2016 19:10:00 +0300 Subject: [PATCH 09/56] -o= option added --- hipamd/src/Cuda2Hip.cpp | 103 +++++++++++++++++++--------------------- 1 file changed, 49 insertions(+), 54 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index f8cf938f32..6716235ea7 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -1,39 +1,29 @@ -//===---- tools/extra/ToolTemplate.cpp - Template for refactoring tool ----===// -// -// The LLVM Compiler Infrastructure -// -// This file is distributed under the University of Illinois Open Source -// License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// -// -// This file implements an empty refactoring tool using the clang tooling. -// The goal is to lower the "barrier to entry" for writing refactoring tools. -// -// Usage: -// tool-template ... -// -// Where is a CMake build directory in which a file named -// compile_commands.json exists (enable -DCMAKE_EXPORT_COMPILE_COMMANDS in -// CMake to get this output). -// -// ... specify the paths of files in the CMake source tree. This path -// is looked up in the compile command database. If the path of a file is -// absolute, it needs to point into CMake's source tree. If the path is -// relative, the current working directory needs to be in the CMake source -// tree and the file must be in a subdirectory of the current working -// directory. "./" prefixes in the relative files will be automatically -// removed, but the rest of a relative path must be a suffix of a path in -// the compile command line database. -// -// For example, to use tool-template on all files in a subtree of the -// source tree, use: -// -// /path/in/subtree $ find . -name '*.cpp'| -// xargs tool-template /path/to/build -// -//===----------------------------------------------------------------------===// +/* +Copyright (c) 2015-2016 Advanced Micro Devices, Inc. All rights reserved. +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +*/ +/** + * @file Cuda2Hip.cpp + * + * This file is compiled and linked into clang based hipify tool. + */ #include "clang/ASTMatchers/ASTMatchers.h" #include "clang/ASTMatchers/ASTMatchFinder.h" #include "clang/Basic/SourceManager.h" @@ -470,8 +460,10 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { } // end anonymous namespace // Set up the command line options -static cl::extrahelp CommonHelp(CommonOptionsParser::HelpMessage); static cl::OptionCategory ToolTemplateCategory("CUDA to HIP source translator options"); +static cl::extrahelp MoreHelp( " specify the path of source file\n\n" ); +static cl::opt +OutputFilename("o", cl::desc("Output filename"), cl::value_desc("filename"), cl::cat(ToolTemplateCategory)); int main(int argc, const char **argv) { @@ -479,24 +471,28 @@ int main(int argc, const char **argv) { int Result; - CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory); - std::vector savedSources; - for (auto I : OptionsParser.getSourcePathList()) - { - size_t pos = I.find(".cu"); - if (pos != std::string::npos) - { - std::string dst = I.substr(0, pos) + ".hip.cu"; - std::ifstream source(I, std::ios::binary); - std::ofstream dest(dst, std::ios::binary); - dest << source.rdbuf(); - source.close(); - dest.close(); - savedSources.push_back(dst); + CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory, llvm::cl::Required); + std::string dst = OutputFilename; + std::vector fileSources = OptionsParser.getSourcePathList(); + if (dst.empty()) { + dst = fileSources[0]; + size_t pos = dst.find(".cu"); + if (pos != std::string::npos) { + dst = dst.substr(0, pos) + ".hip.cu"; + } else { + llvm::errs() << "Input .cu file was not specified.\n"; + return 1; } + } else { + dst += ".cu"; } + std::ifstream source(fileSources[0], std::ios::binary); + std::ofstream dest(dst, std::ios::binary); + dest << source.rdbuf(); + source.close(); + dest.close(); - RefactoringTool Tool(OptionsParser.getCompilations(), savedSources); + RefactoringTool Tool(OptionsParser.getCompilations(), dst); ast_matchers::MatchFinder Finder; Cuda2HipCallback Callback(&Tool.getReplacements()); HipifyPPCallbacks PPCallbacks(&Tool.getReplacements()); @@ -547,12 +543,11 @@ int main(int argc, const char **argv) { Result = Rewrite.overwriteChangedFiles(); - for (auto I : savedSources) { - size_t pos = I.find(".cu"); + size_t pos = dst.find(".cu"); if (pos != std::string::npos) { - rename(I.c_str(), I.substr(0, pos).c_str()); + rename(dst.c_str(), dst.substr(0, pos).c_str()); } } return Result; From a5695b1d52bc367acf5670bfbcef471d4746b303 Mon Sep 17 00:00:00 2001 From: atimofee Date: Wed, 24 Feb 2016 19:27:02 +0300 Subject: [PATCH 10/56] TAB deleted --- hipamd/src/Cuda2Hip.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index b5aa763feb..b57472ca15 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -463,7 +463,6 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) { StringRef s = stringLiteral->getString(); - std::pair split = s.split("cuda"); StringRef cuda = split.second; while (!cuda.empty()) { From 36833c78f31443abc056b92b0e652d756b2e0c41 Mon Sep 17 00:00:00 2001 From: atimofee Date: Wed, 24 Feb 2016 21:22:32 +0300 Subject: [PATCH 11/56] String literal bug fixed + string literal processing refactoring --- hipamd/src/Cuda2Hip.cpp | 28 ++++++++++++---------------- 1 file changed, 12 insertions(+), 16 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 83df1c95b1..5a1432a185 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -453,26 +453,22 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) { StringRef s = stringLiteral->getString(); - std::pair split = s.split("cuda"); - StringRef cuda = split.second; - while (!cuda.empty()) { - size_t byteNum = split.first.size(); - cuda = cuda.data() - 4; - std::pair name_pair = cuda.split(' '); - StringRef name = name_pair.first; + size_t begin = 0; + while ((begin = s.find("cuda", begin)) != StringRef::npos) { + const size_t end = s.find_first_of(" ", begin + 4); + StringRef name = s.slice(begin, end); llvm::outs() << "\nToken: <" << name << "> found in string literal " << s << "\n"; StringRef repName = N.cuda2hipRename[name]; - if (!repName.empty()) - { - llvm::outs() << "\nWill be replaced with: <" << repName << ">\n"; - SourceLocation sl = stringLiteral->getLocationOfByte(byteNum, *SM, - Result.Context->getLangOpts(), Result.Context->getTargetInfo()); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + if (!repName.empty()) { + llvm::outs() << "\nWill be replaced with: <" << repName << "\n"; + SourceLocation sl = stringLiteral->getLocationOfByte(begin, *SM, + Result.Context->getLangOpts(), Result.Context->getTargetInfo()); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); Replace->insert(Rep); } - split = name_pair.second.split("cuda"); - cuda = split.second; + if (end == StringRef::npos) break; + begin = end + 1; } } } From 3d5de5305defa5720d602c80c9fa9f315cd3ba25 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Thu, 25 Feb 2016 15:18:14 +0300 Subject: [PATCH 12/56] fixed lit script discovery in standalone build case --- hipamd/CMakeLists.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 8915cc4714..1a6bc3636d 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -15,6 +15,7 @@ if(${HIPIFY_STANDLONE}) link_directories(${LLVM_LIBRARY_DIRS}) add_definitions(${LLVM_DEFINITIONS}) add_llvm_executable( hipify src/Cuda2Hip.cpp ) + find_program(LIT_COMMAND lit) else() set(LLVM_LINK_COMPONENTS From 63df6f915fcc92dc570d57756be5eb4e06c034e2 Mon Sep 17 00:00:00 2001 From: atimofee Date: Thu, 25 Feb 2016 22:54:58 +0300 Subject: [PATCH 13/56] Fixed tool crash on kernels with empty parameter list --- hipamd/src/Cuda2Hip.cpp | 191 +++++++++++++++++++++------------------- 1 file changed, 99 insertions(+), 92 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 5a1432a185..57df437e77 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -307,98 +307,105 @@ namespace { }; class Cuda2HipCallback : public MatchFinder::MatchCallback { - public: - Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} - - void run(const MatchFinder::MatchResult &Result) override { - - SourceManager * SM = Result.SourceManager; - - if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) - { - const FunctionDecl * funcDcl = call->getDirectCallee(); - std::string name = funcDcl->getDeclName().getAsString(); - if (N.cuda2hipRename.count(name)) { - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = call->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); - Replace->insert(Rep); - } - } - - if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) - { - LangOptions DefaultLangOptions; - - const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); - - const ParmVarDecl * pvdFirst = kernelDecl->getParamDecl(0); - const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); - SourceLocation kernelArgListStart(pvdFirst->getLocStart()); - SourceLocation kernelArgListEnd(pvdLast->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); - size_t replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); - std::string outs(SM->getCharacterData(kernelArgListStart), replacementLength); - llvm::outs() << "initial paramlist: " << outs.c_str() << "\n"; - outs = "hipLaunchParm lp, " + outs; - llvm::outs() << "new paramlist: " << outs.c_str() << "\n"; - Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, outs); - Replace->insert(Rep0); - - - std::string name = kernelDecl->getDeclName().getAsString(); - std::string repName = "hipLaunchKernel(HIP_KERNEL_NAME(" + name + "), "; - - - const CallExpr * config = launchKernel->getConfig(); - llvm::outs() << "\nKernel config arguments:\n"; - for (unsigned argno = 0; argno < config->getNumArgs(); argno++) - { - const Expr * arg = config->getArg(argno); - if (!isa(arg)) { - std::string typeCtor = ""; - const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); - - SourceLocation sl(arg->getLocStart()); - SourceLocation el(arg->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); - std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); - llvm::outs() << "args[ " << argno << "]" << outs.c_str() << " <" << pvd->getType().getAsString() << ">\n"; - if (pvd->getType().getAsString().compare("dim3") == 0) - repName += " dim3(" + outs + "),"; - else - repName += " " + outs + ","; - } else - repName += " 0,"; - } - - for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) - { - const Expr * arg = launchKernel->getArg(argno); - SourceLocation sl(arg->getLocStart()); - SourceLocation el(arg->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); - std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); - llvm::outs() << outs.c_str() << "\n"; - repName += " " + outs + ","; - } - repName.pop_back(); - repName += ")"; - size_t length = SM->getCharacterData(clang::Lexer::getLocForEndOfToken(launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - - SM->getCharacterData(launchKernel->getLocStart()); - Replacement Rep(*SM, launchKernel->getLocStart(), length, repName); - Replace->insert(Rep); - } - - if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) - { - if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { - if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { - std::string name = declRef->getDecl()->getNameAsString(); - std::string memberName = threadIdx->getMemberDecl()->getNameAsString(); - size_t pos = memberName.find_first_not_of("__fetch_builtin_"); - memberName = memberName.substr(pos, memberName.length() - pos); + public: + Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} + + void run(const MatchFinder::MatchResult &Result) override { + + SourceManager * SM = Result.SourceManager; + + if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) + { + const FunctionDecl * funcDcl = call->getDirectCallee(); + std::string name = funcDcl->getDeclName().getAsString(); + if (N.cuda2hipRename.count(name)) { + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = call->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } + } + + if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) + { + LangOptions DefaultLangOptions; + StringRef initialParamList; + SmallString<40> XStr; + raw_svector_ostream OS(XStr); + OS << "hipLaunchParm lp"; + const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); + SourceLocation l1 = kernelDecl->getNameInfo().getLocStart(); + l1.dump(*SM);llvm::outs() << "\n"; + SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(l1, clang::tok::l_paren, *SM, DefaultLangOptions, true); + kernelArgListStart.dump(*SM);llvm::outs() << "\n"; + size_t replacementLength = 0; + if (kernelDecl->getNumParams() > 0) { + //const ParmVarDecl * pvdFirst = kernelDecl->getParamDecl(0); + const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); + //kernelArgListStart = SourceLocation(pvdFirst->getLocStart()); + SourceLocation kernelArgListEnd = SourceLocation(pvdLast->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); + replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); + initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); + OS << ", " << initialParamList; + } + + llvm::outs() << "initial paramlist: " << initialParamList << "\n"; + llvm::outs() << "new paramlist: " << OS.str() << "\n"; + Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); + Replace->insert(Rep0); + + XStr.clear(); + OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << kernelDecl->getName() << "), "; + + const CallExpr * config = launchKernel->getConfig(); + llvm::outs() << "\nKernel config arguments:\n"; + for (unsigned argno = 0; argno < config->getNumArgs(); argno++) + { + const Expr * arg = config->getArg(argno); + if (!isa(arg)) { + const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); + + SourceLocation sl(arg->getLocStart()); + SourceLocation el(arg->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + StringRef outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + llvm::outs() << "args[ " << argno << "]" << outs << " <" << pvd->getType().getAsString() << ">\n"; + if (pvd->getType().getAsString().compare("dim3") == 0) + OS << " dim3(" << outs << "),"; + else + OS << " " << outs << ","; + } else + OS << " 0,"; + } + + for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) + { + const Expr * arg = launchKernel->getArg(argno); + SourceLocation sl(arg->getLocStart()); + SourceLocation el(arg->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + llvm::outs() << outs.c_str() << "\n"; + OS << " " << outs << ","; + } + XStr.pop_back(); + OS << ")"; + size_t length = SM->getCharacterData(clang::Lexer::getLocForEndOfToken(launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - + SM->getCharacterData(launchKernel->getLocStart()); + Replacement Rep(*SM, launchKernel->getLocStart(), length, OS.str()); + Replace->insert(Rep); + } + + if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) + { + if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { + if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { + std::string name = declRef->getDecl()->getNameAsString(); + std::string memberName = threadIdx->getMemberDecl()->getNameAsString(); + size_t pos = memberName.find_first_not_of("__fetch_builtin_"); + memberName = memberName.substr(pos, memberName.length() - pos); name += "." + memberName; std::string repName = N.cuda2hipRename[name]; SourceLocation sl = threadIdx->getLocStart(); From 351e7c74eae726557f634c6bc0dc4c00d01ad8e8 Mon Sep 17 00:00:00 2001 From: atimofee Date: Fri, 26 Feb 2016 23:35:27 +0300 Subject: [PATCH 14/56] =?UTF-8?q?1.CUDA=20structure=20types=20(and=20point?= =?UTF-8?q?ers=20to=20the=20types)=20in=20function=20parameter=20declarati?= =?UTF-8?q?on=20conversion=20=20=20=E2=80=93=20DONE.=202.Wrong=20source=20?= =?UTF-8?q?locations=20in=20qualified=20types=20declaration:=20=20?= =?UTF-8?q?=E2=80=93=20FIXED=203.cudaRuntimeGetVersion=20added=20to=20the?= =?UTF-8?q?=20names=20map=204.sizeof=20expression=20matcher=20added,=20exp?= =?UTF-8?q?ression=20handler=20is=20not=20yet=20ready=20-=20upcoming=20soo?= =?UTF-8?q?n?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- hipamd/src/Cuda2Hip.cpp | 58 +++++++++++++++++++++++++++++++++++------ 1 file changed, 50 insertions(+), 8 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 57df437e77..bb02357869 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -183,6 +183,7 @@ namespace { cuda2hipRename["cudaFuncSetCacheConfig"] = "hipFuncSetCacheConfig"; cuda2hipRename["cudaDriverGetVersion"] = "hipDriverGetVersion"; + cuda2hipRename["cudaRuntimeGetVersion"] = "hipRuntimeGetVersion"; // Peer2Peer cuda2hipRename["cudaDeviceCanAccessPeer"] = "hipDeviceCanAccessPeer"; @@ -341,9 +342,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { kernelArgListStart.dump(*SM);llvm::outs() << "\n"; size_t replacementLength = 0; if (kernelDecl->getNumParams() > 0) { - //const ParmVarDecl * pvdFirst = kernelDecl->getParamDecl(0); const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); - //kernelArgListStart = SourceLocation(pvdFirst->getLocStart()); SourceLocation kernelArgListEnd = SourceLocation(pvdLast->getLocEnd()); SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); @@ -441,22 +440,62 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { std::string name = cudaStructVar->getType()->getAsStructureType()->getDecl()->getNameAsString(); std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = cudaStructVar->getLocStart(); + TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); Replace->insert(Rep); } + if (const VarDecl * cudaStructVarPtr = Result.Nodes.getNodeAs("cudaStructVarPtr")) + { + const Type * t = cudaStructVarPtr->getType().getTypePtrOrNull(); + if (t) { + StringRef name = t->getPointeeCXXRecordDecl()->getName(); + StringRef repName = N.cuda2hipRename[name]; + TypeLoc TL = cudaStructVarPtr->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replace->insert(Rep); + } + } + + if (const ParmVarDecl * cudaParamDecl = Result.Nodes.getNodeAs("cudaParamDecl")) { - QualType QT = cudaParamDecl->getOriginalType(); - std::string name = QT.getAsString(); - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = cudaParamDecl->getLocStart(); + QualType QT = cudaParamDecl->getOriginalType().getUnqualifiedType(); + StringRef name = QT.getAsString(); + const Type * t = QT.getTypePtr(); + if (t->isStructureOrClassType()) { + name = t->getAsCXXRecordDecl()->getName(); + } + StringRef repName = N.cuda2hipRename[name]; + TypeLoc TL = cudaParamDecl->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); Replace->insert(Rep); } + + if (const ParmVarDecl * cudaParamDeclPtr = Result.Nodes.getNodeAs("cudaParamDeclPtr")) + { + const Type * pt = cudaParamDeclPtr->getType().getTypePtrOrNull(); + if (pt) { + QualType QT = pt->getPointeeType(); + const Type * t = QT.getTypePtr(); + StringRef name = t->isStructureOrClassType()? + t->getAsCXXRecordDecl()->getName() : StringRef(QT.getAsString()); + StringRef repName = N.cuda2hipRename[name]; + TypeLoc TL = cudaParamDeclPtr->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replace->insert(Rep); + } + } + + if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) { StringRef s = stringLiteral->getString(); @@ -530,7 +569,10 @@ int main(int argc, const char **argv) { Finder.addMatcher(declRefExpr(isExpansionInMainFile(), to(enumConstantDecl(matchesName("cuda.*")))).bind("cudaEnumConstantRef"), &Callback); Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))).bind("cudaEnumConstantDecl"), &Callback); Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); + Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(pointsTo(cxxRecordDecl(matchesName("cuda.*"))))).bind("cudaStructVarPtr"), &Callback); Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); + Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(pointsTo(namedDecl(matchesName("cuda.*"))))).bind("cudaParamDeclPtr"), &Callback); + Finder.addMatcher(expr(sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration(cxxRecordDecl(matchesName("cuda.*"))))))).bind("cudaStructSizeOf"), &Callback); Finder.addMatcher(stringLiteral().bind("stringLiteral"), &Callback); auto action = newFrontendActionFactory(&Finder, &PPCallbacks); From 73f8574d1bfa08dc838d6632cf079f8ea32a4845 Mon Sep 17 00:00:00 2001 From: atimofee Date: Mon, 29 Feb 2016 20:27:38 +0300 Subject: [PATCH 15/56] CUDA type names in sizeof() expression conversion added --- hipamd/src/Cuda2Hip.cpp | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index bb02357869..c86a80bfb7 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -517,6 +517,20 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { begin = end + 1; } } + + if (const UnaryExprOrTypeTraitExpr * expr = Result.Nodes.getNodeAs("cudaStructSizeOf")) + { + TypeSourceInfo * typeInfo = expr->getArgumentTypeInfo(); + QualType QT = typeInfo->getType().getUnqualifiedType(); + const Type * type = QT.getTypePtr(); + StringRef name = type->getAsCXXRecordDecl()->getName(); + StringRef repName = N.cuda2hipRename[name]; + TypeLoc TL = typeInfo->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replace->insert(Rep); + } } private: From 724519bb9c55c7f713ebf999a4ff3edabf032bb0 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Tue, 1 Mar 2016 18:15:54 +0300 Subject: [PATCH 16/56] Fix hipify tool discovery in lit test for standalone build case --- hipamd/test/CMakeLists.txt | 4 ++-- hipamd/test/lit.cfg | 1 + hipamd/test/lit.site.cfg.in | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/hipamd/test/CMakeLists.txt b/hipamd/test/CMakeLists.txt index 4f74091b0b..5a0250381d 100644 --- a/hipamd/test/CMakeLists.txt +++ b/hipamd/test/CMakeLists.txt @@ -6,7 +6,7 @@ if( NOT PYTHONINTERP_FOUND ) "Please install Python or specify the PYTHON_EXECUTABLE CMake variable.") endif() -set(BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR} ) +set(BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/.. ) configure_file( ${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.in @@ -16,7 +16,7 @@ configure_file( add_lit_testsuite(check-hipify "Running HIPify regression tests" ${CMAKE_CURRENT_SOURCE_DIR} PARAMS site_config=${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg - DEPENDS hipify + DEPENDS hipify FileCheck lit ) add_custom_target(check) diff --git a/hipamd/test/lit.cfg b/hipamd/test/lit.cfg index 775cdbf0d4..d9606b48fc 100644 --- a/hipamd/test/lit.cfg +++ b/hipamd/test/lit.cfg @@ -51,4 +51,5 @@ if not tool_path: lit_config.note('Did not find ' + tool_name + ' in ' + llvm_tools_dir) tool_path = llvm_tools_dir + '/' + tool_name config.substitutions.append((tool_name, tool_path)) +config.substitutions.append(("hipify", obj_root+"/hipify")) diff --git a/hipamd/test/lit.site.cfg.in b/hipamd/test/lit.site.cfg.in index 6fc35440d4..4511316ac7 100644 --- a/hipamd/test/lit.site.cfg.in +++ b/hipamd/test/lit.site.cfg.in @@ -1,7 +1,7 @@ import sys config.llvm_tools_dir = "@LLVM_TOOLS_BINARY_DIR@" -config.obj_root = "@CMAKE_CURRENT_BINARY_DIR@" +config.obj_root = "@BINARY_DIR@" # Support substitution of the tools and libs dirs with user parameters. This is # used when we can't determine the tool dir at configuration time. From 59ddc9230edaedf9143a2d51a0374fbed31551c3 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Tue, 1 Mar 2016 19:46:55 +0300 Subject: [PATCH 17/56] minor spaces cleanup --- hipamd/CMakeLists.txt | 3 +- hipamd/src/Cuda2Hip.cpp | 246 ++++++++++++++++++++-------------------- 2 files changed, 124 insertions(+), 125 deletions(-) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 1a6bc3636d..3348056faf 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -14,9 +14,8 @@ if(${HIPIFY_STANDLONE}) include_directories(${LLVM_INCLUDE_DIRS}) link_directories(${LLVM_LIBRARY_DIRS}) add_definitions(${LLVM_DEFINITIONS}) - add_llvm_executable( hipify src/Cuda2Hip.cpp ) + add_llvm_executable(hipify src/Cuda2Hip.cpp ) find_program(LIT_COMMAND lit) - else() set(LLVM_LINK_COMPONENTS Option diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index c86a80bfb7..253a870c5c 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -157,7 +157,7 @@ namespace { cuda2hipRename["cudaStreamDefault"] = "hipStreamDefault"; cuda2hipRename["cudaStreamNonBlocking"] = "hipStreamNonBlocking"; - // Other synchronization + // Other synchronization cuda2hipRename["cudaDeviceSynchronize"] = "hipDeviceSynchronize"; cuda2hipRename["cudaThreadSynchronize"] = "hipDeviceSynchronize"; // translate deprecated cudaThreadSynchronize cuda2hipRename["cudaDeviceReset"] = "hipDeviceReset"; @@ -165,7 +165,7 @@ namespace { cuda2hipRename["cudaSetDevice"] = "hipSetDevice"; cuda2hipRename["cudaGetDevice"] = "hipGetDevice"; - // Device + // Device cuda2hipRename["cudaDeviceProp"] = "hipDeviceProp_t"; cuda2hipRename["cudaGetDeviceProperties"] = "hipDeviceGetProperties"; @@ -292,11 +292,11 @@ namespace { } } - void EndOfMainFile() override - { - + void EndOfMainFile() override + { + } - + bool SeenEnd; void setSourceManager(SourceManager * sm) { _sm = sm; } @@ -308,103 +308,103 @@ namespace { }; class Cuda2HipCallback : public MatchFinder::MatchCallback { - public: + public: Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} - + void run(const MatchFinder::MatchResult &Result) override { - - SourceManager * SM = Result.SourceManager; - - if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) - { - const FunctionDecl * funcDcl = call->getDirectCallee(); - std::string name = funcDcl->getDeclName().getAsString(); - if (N.cuda2hipRename.count(name)) { - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = call->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); - Replace->insert(Rep); - } - } - - if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) - { - LangOptions DefaultLangOptions; - StringRef initialParamList; - SmallString<40> XStr; - raw_svector_ostream OS(XStr); - OS << "hipLaunchParm lp"; - const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); - SourceLocation l1 = kernelDecl->getNameInfo().getLocStart(); - l1.dump(*SM);llvm::outs() << "\n"; - SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(l1, clang::tok::l_paren, *SM, DefaultLangOptions, true); - kernelArgListStart.dump(*SM);llvm::outs() << "\n"; - size_t replacementLength = 0; - if (kernelDecl->getNumParams() > 0) { - const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); - SourceLocation kernelArgListEnd = SourceLocation(pvdLast->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); - replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); - initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); - OS << ", " << initialParamList; - } - - llvm::outs() << "initial paramlist: " << initialParamList << "\n"; - llvm::outs() << "new paramlist: " << OS.str() << "\n"; - Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); - Replace->insert(Rep0); - - XStr.clear(); - OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << kernelDecl->getName() << "), "; - - const CallExpr * config = launchKernel->getConfig(); - llvm::outs() << "\nKernel config arguments:\n"; - for (unsigned argno = 0; argno < config->getNumArgs(); argno++) - { - const Expr * arg = config->getArg(argno); - if (!isa(arg)) { - const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); - - SourceLocation sl(arg->getLocStart()); - SourceLocation el(arg->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); - StringRef outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); - llvm::outs() << "args[ " << argno << "]" << outs << " <" << pvd->getType().getAsString() << ">\n"; - if (pvd->getType().getAsString().compare("dim3") == 0) - OS << " dim3(" << outs << "),"; - else - OS << " " << outs << ","; - } else - OS << " 0,"; - } - - for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) - { - const Expr * arg = launchKernel->getArg(argno); - SourceLocation sl(arg->getLocStart()); - SourceLocation el(arg->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); - std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); - llvm::outs() << outs.c_str() << "\n"; - OS << " " << outs << ","; - } - XStr.pop_back(); - OS << ")"; - size_t length = SM->getCharacterData(clang::Lexer::getLocForEndOfToken(launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - - SM->getCharacterData(launchKernel->getLocStart()); - Replacement Rep(*SM, launchKernel->getLocStart(), length, OS.str()); - Replace->insert(Rep); - } - - if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) - { - if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { - if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { - std::string name = declRef->getDecl()->getNameAsString(); - std::string memberName = threadIdx->getMemberDecl()->getNameAsString(); - size_t pos = memberName.find_first_not_of("__fetch_builtin_"); - memberName = memberName.substr(pos, memberName.length() - pos); + + SourceManager * SM = Result.SourceManager; + + if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) + { + const FunctionDecl * funcDcl = call->getDirectCallee(); + std::string name = funcDcl->getDeclName().getAsString(); + if (N.cuda2hipRename.count(name)) { + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = call->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } + } + + if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) + { + LangOptions DefaultLangOptions; + StringRef initialParamList; + SmallString<40> XStr; + raw_svector_ostream OS(XStr); + OS << "hipLaunchParm lp"; + const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); + SourceLocation l1 = kernelDecl->getNameInfo().getLocStart(); + l1.dump(*SM);llvm::outs() << "\n"; + SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(l1, clang::tok::l_paren, *SM, DefaultLangOptions, true); + kernelArgListStart.dump(*SM);llvm::outs() << "\n"; + size_t replacementLength = 0; + if (kernelDecl->getNumParams() > 0) { + const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); + SourceLocation kernelArgListEnd = SourceLocation(pvdLast->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); + replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); + initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); + OS << ", " << initialParamList; + } + + llvm::outs() << "initial paramlist: " << initialParamList << "\n"; + llvm::outs() << "new paramlist: " << OS.str() << "\n"; + Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); + Replace->insert(Rep0); + + XStr.clear(); + OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << kernelDecl->getName() << "), "; + + const CallExpr * config = launchKernel->getConfig(); + llvm::outs() << "\nKernel config arguments:\n"; + for (unsigned argno = 0; argno < config->getNumArgs(); argno++) + { + const Expr * arg = config->getArg(argno); + if (!isa(arg)) { + const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); + + SourceLocation sl(arg->getLocStart()); + SourceLocation el(arg->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + StringRef outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + llvm::outs() << "args[ " << argno << "]" << outs << " <" << pvd->getType().getAsString() << ">\n"; + if (pvd->getType().getAsString().compare("dim3") == 0) + OS << " dim3(" << outs << "),"; + else + OS << " " << outs << ","; + } else + OS << " 0,"; + } + + for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) + { + const Expr * arg = launchKernel->getArg(argno); + SourceLocation sl(arg->getLocStart()); + SourceLocation el(arg->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + llvm::outs() << outs.c_str() << "\n"; + OS << " " << outs << ","; + } + XStr.pop_back(); + OS << ")"; + size_t length = SM->getCharacterData(clang::Lexer::getLocForEndOfToken(launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - + SM->getCharacterData(launchKernel->getLocStart()); + Replacement Rep(*SM, launchKernel->getLocStart(), length, OS.str()); + Replace->insert(Rep); + } + + if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) + { + if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { + if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { + std::string name = declRef->getDecl()->getNameAsString(); + std::string memberName = threadIdx->getMemberDecl()->getNameAsString(); + size_t pos = memberName.find_first_not_of("__fetch_builtin_"); + memberName = memberName.substr(pos, memberName.length() - pos); name += "." + memberName; std::string repName = N.cuda2hipRename[name]; SourceLocation sl = threadIdx->getLocStart(); @@ -498,24 +498,24 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) { - StringRef s = stringLiteral->getString(); - size_t begin = 0; - while ((begin = s.find("cuda", begin)) != StringRef::npos) { - const size_t end = s.find_first_of(" ", begin + 4); - StringRef name = s.slice(begin, end); - llvm::outs() << "\nToken: <" << name << "> found in string literal " << s << "\n"; - StringRef repName = N.cuda2hipRename[name]; - if (!repName.empty()) { - llvm::outs() << "\nWill be replaced with: <" << repName << "\n"; - SourceLocation sl = stringLiteral->getLocationOfByte(begin, *SM, - Result.Context->getLangOpts(), Result.Context->getTargetInfo()); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); - Replace->insert(Rep); - } - if (end == StringRef::npos) break; - begin = end + 1; - } + StringRef s = stringLiteral->getString(); + size_t begin = 0; + while ((begin = s.find("cuda", begin)) != StringRef::npos) { + const size_t end = s.find_first_of(" ", begin + 4); + StringRef name = s.slice(begin, end); + llvm::outs() << "\nToken: <" << name << "> found in string literal " << s << "\n"; + StringRef repName = N.cuda2hipRename[name]; + if (!repName.empty()) { + llvm::outs() << "\nWill be replaced with: <" << repName << "\n"; + SourceLocation sl = stringLiteral->getLocationOfByte(begin, *SM, + Result.Context->getLangOpts(), Result.Context->getTargetInfo()); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replace->insert(Rep); + } + if (end == StringRef::npos) break; + begin = end + 1; + } } if (const UnaryExprOrTypeTraitExpr * expr = Result.Nodes.getNodeAs("cudaStructSizeOf")) @@ -551,7 +551,7 @@ int main(int argc, const char **argv) { llvm::sys::PrintStackTraceOnErrorSignal(); int Result; - + CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory, llvm::cl::Required); std::string dst = OutputFilename; std::vector fileSources = OptionsParser.getSourcePathList(); @@ -584,9 +584,9 @@ int main(int argc, const char **argv) { Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))).bind("cudaEnumConstantDecl"), &Callback); Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(pointsTo(cxxRecordDecl(matchesName("cuda.*"))))).bind("cudaStructVarPtr"), &Callback); - Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); + Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(pointsTo(namedDecl(matchesName("cuda.*"))))).bind("cudaParamDeclPtr"), &Callback); - Finder.addMatcher(expr(sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration(cxxRecordDecl(matchesName("cuda.*"))))))).bind("cudaStructSizeOf"), &Callback); + Finder.addMatcher(expr(sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration(cxxRecordDecl(matchesName("cuda.*"))))))).bind("cudaStructSizeOf"), &Callback); Finder.addMatcher(stringLiteral().bind("stringLiteral"), &Callback); auto action = newFrontendActionFactory(&Finder, &PPCallbacks); @@ -605,7 +605,7 @@ int main(int argc, const char **argv) { Tool.clearArgumentsAdjusters(); } - + LangOptions DefaultLangOptions; IntrusiveRefCntPtr DiagOpts = new DiagnosticOptions(); TextDiagnosticPrinter DiagnosticPrinter(llvm::errs(), &*DiagOpts); From 83bdafe809f8552776cc620f2e8b3c62a749714e Mon Sep 17 00:00:00 2001 From: atimofee Date: Tue, 1 Mar 2016 21:42:30 +0300 Subject: [PATCH 18/56] Macro expansion processing refactoring - initial stage --- hipamd/src/Cuda2Hip.cpp | 124 +++++++++++++++++++++++++++++----------- 1 file changed, 91 insertions(+), 33 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index c86a80bfb7..c2217c5bf0 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -42,6 +42,7 @@ THE SOFTWARE. #include "clang/Frontend/CompilerInstance.h" #include "clang/Lex/Preprocessor.h" #include "clang/Lex/PPCallbacks.h" +#include "clang/Lex/MacroArgs.h" #include #include @@ -222,7 +223,7 @@ namespace { struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { HipifyPPCallbacks(Replacements * R) - : SeenEnd(false), _sm(nullptr), Replace(R) + : SeenEnd(false), _sm(nullptr), _pp(nullptr), Replace(R) { } @@ -233,6 +234,7 @@ namespace { setSourceManager(&SM); PP.addPPCallbacks(std::unique_ptr(this)); PP.Retain(); + setPreprocessor(&PP); return true; } @@ -279,7 +281,8 @@ namespace { if (N.cuda2hipRename.count(name)) { StringRef repName = N.cuda2hipRename[name]; llvm::errs() << "\nIdentifier " << name - << " found in definition of macro " << MacroNameTok.getIdentifierInfo()->getName() << "\n"; + << " found in definition of macro " + << MacroNameTok.getIdentifierInfo()->getName() << "\n"; llvm::errs() << "\nwill be replaced with: " << repName << "\n"; SourceLocation sl = T.getLocation(); llvm::errs() << "\nSourceLocation: ";sl.dump(*_sm); @@ -292,6 +295,68 @@ namespace { } } + virtual void MacroExpands(const Token &MacroNameTok, + const MacroDefinition &MD, SourceRange Range, + const MacroArgs *Args) override + { + if (_sm->isWrittenInMainFile(Range.getBegin())) + { + for (unsigned int i = 0; Args && i < MD.getMacroInfo()->getNumArgs(); i++) + { + StringRef macroName = MacroNameTok.getIdentifierInfo()->getName(); + std::vector toks; + // Code below is a kind of stolen from 'MacroArgs::getPreExpArgument' + // to workaround the 'const' MacroArgs passed into this hook. + const Token * start = Args->getUnexpArgument(i); + size_t len = Args->getArgLength(start) + 1; + _pp->EnterTokenStream(ArrayRef(start,len), false); + do { + toks.push_back(Token()); + Token & tk = toks.back(); + _pp->Lex(tk); + } while (toks.back().isNot(tok::eof)); + _pp->RemoveTopOfLexerStack(); + // end of stolen code + for (auto tok : toks) { + if (tok.isAnyIdentifier()) + { + StringRef name = tok.getIdentifierInfo()->getName(); + if (N.cuda2hipRename.count(name)) { + StringRef repName = N.cuda2hipRename[name]; + llvm::errs() << "\nIdentifier " << name + << " found as an actual argument in expansion of macro " + << macroName << "\n"; + llvm::errs() << "\nwill be replaced with: " << repName << "\n"; + SourceLocation sl = tok.getLocation(); + Replacement Rep(*_sm, sl, name.size(), repName); + Replace->insert(Rep); + } + } + if (tok.is(tok::string_literal)) + { + StringRef s(tok.getLiteralData(), tok.getLength()); + size_t begin = 0; + while ((begin = s.find("cuda", begin)) != StringRef::npos) { + const size_t end = s.find_first_of(" ", begin + 4); + StringRef name = s.slice(begin, end); + llvm::outs() << "\nToken: <" << name << "> found in string literal '" + << s << "' as argument in expansion of macro '" << macroName << "'\n"; + StringRef repName = N.cuda2hipRename[name]; + if (!repName.empty()) { + llvm::outs() << "\nWill be replaced with: <" << repName << "\n"; + SourceLocation sl = tok.getLocation().getLocWithOffset(begin); + Replacement Rep(*_sm, sl, name.size(), repName); + Replace->insert(Rep); + } + if (end == StringRef::npos) break; + begin = end + 1; + } + } + } + } + } + } + void EndOfMainFile() override { @@ -299,10 +364,13 @@ namespace { bool SeenEnd; void setSourceManager(SourceManager * sm) { _sm = sm; } + void setPreprocessor (Preprocessor * pp) { _pp = pp; } private: SourceManager * _sm; + Preprocessor * _pp; + Replacements * Replace; struct hipName N; }; @@ -315,18 +383,17 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { SourceManager * SM = Result.SourceManager; - if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) - { - const FunctionDecl * funcDcl = call->getDirectCallee(); - std::string name = funcDcl->getDeclName().getAsString(); - if (N.cuda2hipRename.count(name)) { - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = call->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); - Replace->insert(Rep); - } - } + if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) + { + const FunctionDecl * funcDcl = call->getDirectCallee(); + std::string name = funcDcl->getDeclName().getAsString(); + if (N.cuda2hipRename.count(name)) { + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = call->getLocStart(); + Replacement Rep(*SM, sl, name.length(), repName); + Replace->insert(Rep); + } + } if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) { @@ -408,8 +475,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { name += "." + memberName; std::string repName = N.cuda2hipRename[name]; SourceLocation sl = threadIdx->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replacement Rep(*SM, sl, name.length(), repName); Replace->insert(Rep); } } @@ -420,8 +486,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { std::string name = cudaEnumConstantRef->getDecl()->getNameAsString(); std::string repName = N.cuda2hipRename[name]; SourceLocation sl = cudaEnumConstantRef->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replacement Rep(*SM, sl, name.length(), repName); Replace->insert(Rep); } @@ -430,8 +495,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { std::string name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); std::string repName = N.cuda2hipRename[name]; SourceLocation sl = cudaEnumConstantDecl->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replacement Rep(*SM, sl, name.length(), repName); Replace->insert(Rep); } @@ -442,8 +506,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { std::string repName = N.cuda2hipRename[name]; TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replacement Rep(*SM, sl, name.length(), repName); Replace->insert(Rep); } @@ -455,8 +518,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { StringRef repName = N.cuda2hipRename[name]; TypeLoc TL = cudaStructVarPtr->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } } @@ -473,8 +535,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { StringRef repName = N.cuda2hipRename[name]; TypeLoc TL = cudaParamDecl->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } @@ -489,8 +550,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { StringRef repName = N.cuda2hipRename[name]; TypeLoc TL = cudaParamDeclPtr->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } } @@ -509,8 +569,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { llvm::outs() << "\nWill be replaced with: <" << repName << "\n"; SourceLocation sl = stringLiteral->getLocationOfByte(begin, *SM, Result.Context->getLangOpts(), Result.Context->getTargetInfo()); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } if (end == StringRef::npos) break; @@ -524,11 +583,10 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { QualType QT = typeInfo->getType().getUnqualifiedType(); const Type * type = QT.getTypePtr(); StringRef name = type->getAsCXXRecordDecl()->getName(); - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name]; TypeLoc TL = typeInfo->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } } From b96797dcd9989f402d60ed458f4bf734e4f2fc2a Mon Sep 17 00:00:00 2001 From: atimofee Date: Wed, 2 Mar 2016 17:22:06 +0300 Subject: [PATCH 19/56] String literals processing unified --- hipamd/src/Cuda2Hip.cpp | 60 +++++++++++++++++++---------------------- 1 file changed, 27 insertions(+), 33 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 1c4b812506..07529c8e2f 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -221,6 +221,31 @@ namespace { DenseMap cuda2hipRename; }; + StringRef unquoteStr(StringRef s) { + if (s.size() > 1 && s.front() == '"' && s.back() == '"') + return s.substr(1, s.size()-2); + return s; + } + + void processString(StringRef s, struct hipName & map, + Replacements * Replace, SourceManager & SM, SourceLocation start) + { + size_t begin = 0; + while ((begin = s.find("cuda", begin)) != StringRef::npos) { + const size_t end = s.find_first_of(" ", begin + 4); + StringRef name = s.slice(begin, end); + StringRef repName = map.cuda2hipRename[name]; + if (!repName.empty()) { + SourceLocation sl = start.getLocWithOffset(begin + 1); + Replacement Rep(SM, sl, name.size(), repName); + Replace->insert(Rep); + } + if (end == StringRef::npos) break; + begin = end + 1; + } + } + + struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { HipifyPPCallbacks(Replacements * R) : SeenEnd(false), _sm(nullptr), _pp(nullptr), Replace(R) @@ -335,22 +360,7 @@ namespace { if (tok.is(tok::string_literal)) { StringRef s(tok.getLiteralData(), tok.getLength()); - size_t begin = 0; - while ((begin = s.find("cuda", begin)) != StringRef::npos) { - const size_t end = s.find_first_of(" ", begin + 4); - StringRef name = s.slice(begin, end); - llvm::outs() << "\nToken: <" << name << "> found in string literal '" - << s << "' as argument in expansion of macro '" << macroName << "'\n"; - StringRef repName = N.cuda2hipRename[name]; - if (!repName.empty()) { - llvm::outs() << "\nWill be replaced with: <" << repName << "\n"; - SourceLocation sl = tok.getLocation().getLocWithOffset(begin); - Replacement Rep(*_sm, sl, name.size(), repName); - Replace->insert(Rep); - } - if (end == StringRef::npos) break; - begin = end + 1; - } + processString(unquoteStr(s), N, Replace, *_sm, tok.getLocation()); } } } @@ -560,23 +570,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) { StringRef s = stringLiteral->getString(); - size_t begin = 0; - while ((begin = s.find("cuda", begin)) != StringRef::npos) { - const size_t end = s.find_first_of(" ", begin + 4); - StringRef name = s.slice(begin, end); - llvm::outs() << "\nToken: <" << name << "> found in string literal " << s << "\n"; - StringRef repName = N.cuda2hipRename[name]; - if (!repName.empty()) { - llvm::outs() << "\nWill be replaced with: <" << repName << "\n"; - SourceLocation sl = stringLiteral->getLocationOfByte(begin, *SM, - Result.Context->getLangOpts(), Result.Context->getTargetInfo()); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); - Replace->insert(Rep); - } - if (end == StringRef::npos) break; - begin = end + 1; - } + processString(s, N, Replace, *SM, stringLiteral->getLocStart()); } if (const UnaryExprOrTypeTraitExpr * expr = Result.Nodes.getNodeAs("cudaStructSizeOf")) From dcdcd5450b9512d809bb1b2a6384053ff0703fce Mon Sep 17 00:00:00 2001 From: dfukalov Date: Wed, 2 Mar 2016 18:01:51 +0300 Subject: [PATCH 20/56] add FE option "-std=c++11" by default --- hipamd/src/Cuda2Hip.cpp | 19 +++++++++---------- 1 file changed, 9 insertions(+), 10 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 1c4b812506..8b5b5c9d1e 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -299,17 +299,17 @@ namespace { const MacroDefinition &MD, SourceRange Range, const MacroArgs *Args) override { - if (_sm->isWrittenInMainFile(Range.getBegin())) + if (_sm->isWrittenInMainFile(Range.getBegin())) { for (unsigned int i = 0; Args && i < MD.getMacroInfo()->getNumArgs(); i++) { StringRef macroName = MacroNameTok.getIdentifierInfo()->getName(); std::vector toks; - // Code below is a kind of stolen from 'MacroArgs::getPreExpArgument' - // to workaround the 'const' MacroArgs passed into this hook. - const Token * start = Args->getUnexpArgument(i); - size_t len = Args->getArgLength(start) + 1; - _pp->EnterTokenStream(ArrayRef(start,len), false); + // Code below is a kind of stolen from 'MacroArgs::getPreExpArgument' + // to workaround the 'const' MacroArgs passed into this hook. + const Token * start = Args->getUnexpArgument(i); + size_t len = Args->getArgLength(start) + 1; + _pp->EnterTokenStream(ArrayRef(start,len), false); do { toks.push_back(Token()); Token & tk = toks.back(); @@ -657,10 +657,9 @@ int main(int argc, const char **argv) { for (auto Stage : compilationStages) { - Tool.appendArgumentsAdjuster(combineAdjusters( - getInsertArgumentAdjuster(Stage, ArgumentInsertPosition::BEGIN), - getClangSyntaxOnlyAdjuster())); - + Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster(Stage, ArgumentInsertPosition::BEGIN)); + Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster("-std=c++11")); + Tool.appendArgumentsAdjuster(getClangSyntaxOnlyAdjuster()); Result = Tool.run(action.get()); Tool.clearArgumentsAdjusters(); From 52a51c704d0a2848c9ac955b1a0714605669f23f Mon Sep 17 00:00:00 2001 From: dfukalov Date: Wed, 2 Mar 2016 19:58:45 +0300 Subject: [PATCH 21/56] fixed line endings to unix format as in clang/llvm --- hipamd/src/Cuda2Hip.cpp | 1384 +++++++++++++++++++-------------------- 1 file changed, 692 insertions(+), 692 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 28ae058754..42d3ca836f 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -1,692 +1,692 @@ -/* -Copyright (c) 2015-2016 Advanced Micro Devices, Inc. All rights reserved. - -Permission is hereby granted, free of charge, to any person obtaining a copy -of this software and associated documentation files (the "Software"), to deal -in the Software without restriction, including without limitation the rights -to use, copy, modify, merge, publish, distribute, sublicense, and/or sell -copies of the Software, and to permit persons to whom the Software is -furnished to do so, subject to the following conditions: - -The above copyright notice and this permission notice shall be included in -all copies or substantial portions of the Software. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, -OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN -THE SOFTWARE. -*/ -/** - * @file Cuda2Hip.cpp - * - * This file is compiled and linked into clang based hipify tool. - */ -#include "clang/ASTMatchers/ASTMatchers.h" -#include "clang/ASTMatchers/ASTMatchFinder.h" -#include "clang/Basic/SourceManager.h" -#include "clang/Frontend/FrontendActions.h" -#include "clang/Lex/Lexer.h" -#include "clang/Tooling/CommonOptionsParser.h" -#include "clang/Tooling/Refactoring.h" -#include "clang/Tooling/Tooling.h" -#include "llvm/Support/CommandLine.h" -#include "llvm/Support/MemoryBuffer.h" -#include "llvm/Support/Signals.h" -#include "llvm/Support/Debug.h" -#include "clang/Frontend/TextDiagnosticPrinter.h" -#include "clang/Rewrite/Core/Rewriter.h" -#include "clang/Lex/MacroInfo.h" -#include "clang/Frontend/CompilerInstance.h" -#include "clang/Lex/Preprocessor.h" -#include "clang/Lex/PPCallbacks.h" -#include "clang/Lex/MacroArgs.h" - -#include -#include - -using namespace clang; -using namespace clang::ast_matchers; -using namespace clang::tooling; -using namespace llvm; - -#define DEBUG_TYPE "cuda2hip" - -namespace { - struct hipName { - hipName() { - // defines - cuda2hipRename["__CUDACC__"] = "__HIPCC__"; - - // includes - cuda2hipRename["cuda_runtime.h"] = "hip_runtime.h"; - cuda2hipRename["cuda_runtime_api.h"] = "hip_runtime_api.h"; - - // Error codes and return types: - cuda2hipRename["cudaError_t"] = "hipError_t"; - cuda2hipRename["cudaError"] = "hipError"; - cuda2hipRename["cudaSuccess"] = "hipSuccess"; - - cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; - cuda2hipRename["cudaErrorMemoryAllocation"] = "hipErrorMemoryAllocation"; - cuda2hipRename["cudaErrorMemoryFree"] = "hipErrorMemoryFree"; - cuda2hipRename["cudaErrorUnknownSymbol"] = "hipErrorUnknownSymbol"; - cuda2hipRename["cudaErrorOutOfResources"] = "hipErrorOutOfResources"; - cuda2hipRename["cudaErrorInvalidValue"] = "hipErrorInvalidValue"; - cuda2hipRename["cudaErrorInvalidResourceHandle"] = "hipErrorInvalidResourceHandle"; - cuda2hipRename["cudaErrorInvalidDevice"] = "hipErrorInvalidDevice"; - cuda2hipRename["cudaErrorNoDevice"] = "hipErrorNoDevice"; - cuda2hipRename["cudaErrorNotReady"] = "hipErrorNotReady"; - cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; - - // error APIs: - cuda2hipRename["cudaGetLastError"] = "hipGetLastError"; - cuda2hipRename["cudaPeekAtLastError"] = "hipPeekAtLastError"; - cuda2hipRename["cudaGetErrorName"] = "hipGetErrorName"; - cuda2hipRename["cudaGetErrorString"] = "hipGetErrorString"; - - // Memcpy - cuda2hipRename["cudaMemcpy"] = "hipMemcpy"; - cuda2hipRename["cudaMemcpyHostToHost"] = "hipMemcpyHostToHost"; - cuda2hipRename["cudaMemcpyHostToDevice"] = "hipMemcpyHostToDevice"; - cuda2hipRename["cudaMemcpyDeviceToHost"] = "hipMemcpyDeviceToHost"; - cuda2hipRename["cudaMemcpyDeviceToDevice"] = "hipMemcpyDeviceToDevice"; - cuda2hipRename["cudaMemcpyDefault"] = "hipMemcpyDefault"; - cuda2hipRename["cudaMemcpyToSymbol"] = "hipMemcpyToSymbol"; - cuda2hipRename["cudaMemset"] = "hipMemset"; - cuda2hipRename["cudaMemsetAsync"] = "hipMemsetAsync"; - cuda2hipRename["cudaMemcpyAsync"] = "hipMemcpyAsync"; - cuda2hipRename["cudaMemGetInfo"] = "hipMemGetInfo"; - cuda2hipRename["cudaMemcpyKind"] = "hipMemcpyKind"; - - // Memory management : - cuda2hipRename["cudaMalloc"] = "hipMalloc"; - cuda2hipRename["cudaMallocHost"] = "hipMallocHost"; - cuda2hipRename["cudaFree"] = "hipFree"; - cuda2hipRename["cudaFreeHost"] = "hipFreeHost"; - - // Coordinate Indexing and Dimensions: - cuda2hipRename["threadIdx.x"] = "hipThreadIdx_x"; - cuda2hipRename["threadIdx.y"] = "hipThreadIdx_y"; - cuda2hipRename["threadIdx.z"] = "hipThreadIdx_z"; - - cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; - cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; - cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; - - cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; - cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; - cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; - - cuda2hipRename["gridDim.x"] = "hipGridDim_x"; - cuda2hipRename["gridDim.y"] = "hipGridDim_y"; - cuda2hipRename["gridDim.z"] = "hipGridDim_z"; - - cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; - cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; - cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; - - cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; - cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; - cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; - - cuda2hipRename["gridDim.x"] = "hipGridDim_x"; - cuda2hipRename["gridDim.y"] = "hipGridDim_y"; - cuda2hipRename["gridDim.z"] = "hipGridDim_z"; - - - cuda2hipRename["warpSize"] = "hipWarpSize"; - - // Events - cuda2hipRename["cudaEvent_t"] = "hipEvent_t"; - cuda2hipRename["cudaEventCreate"] = "hipEventCreate"; - cuda2hipRename["cudaEventCreateWithFlags"] = "hipEventCreateWithFlags"; - cuda2hipRename["cudaEventDestroy"] = "hipEventDestroy"; - cuda2hipRename["cudaEventRecord"] = "hipEventRecord"; - cuda2hipRename["cudaEventElapsedTime"] = "hipEventElapsedTime"; - cuda2hipRename["cudaEventSynchronize"] = "hipEventSynchronize"; - - // Streams - cuda2hipRename["cudaStream_t"] = "hipStream_t"; - cuda2hipRename["cudaStreamCreate"] = "hipStreamCreate"; - cuda2hipRename["cudaStreamCreateWithFlags"] = "hipStreamCreateWithFlags"; - cuda2hipRename["cudaStreamDestroy"] = "hipStreamDestroy"; - cuda2hipRename["cudaStreamWaitEvent"] = "hipStreamWaitEven"; - cuda2hipRename["cudaStreamSynchronize"] = "hipStreamSynchronize"; - cuda2hipRename["cudaStreamDefault"] = "hipStreamDefault"; - cuda2hipRename["cudaStreamNonBlocking"] = "hipStreamNonBlocking"; - - // Other synchronization - cuda2hipRename["cudaDeviceSynchronize"] = "hipDeviceSynchronize"; - cuda2hipRename["cudaThreadSynchronize"] = "hipDeviceSynchronize"; // translate deprecated cudaThreadSynchronize - cuda2hipRename["cudaDeviceReset"] = "hipDeviceReset"; - cuda2hipRename["cudaThreadExit"] = "hipDeviceReset"; // translate deprecated cudaThreadExit - cuda2hipRename["cudaSetDevice"] = "hipSetDevice"; - cuda2hipRename["cudaGetDevice"] = "hipGetDevice"; - - // Device - cuda2hipRename["cudaDeviceProp"] = "hipDeviceProp_t"; - cuda2hipRename["cudaGetDeviceProperties"] = "hipDeviceGetProperties"; - - // Cache config - cuda2hipRename["cudaDeviceSetCacheConfig"] = "hipDeviceSetCacheConfig"; - cuda2hipRename["cudaThreadSetCacheConfig"] = "hipDeviceSetCacheConfig"; // translate deprecated - cuda2hipRename["cudaDeviceGetCacheConfig"] = "hipDeviceGetCacheConfig"; - cuda2hipRename["cudaThreadGetCacheConfig"] = "hipDeviceGetCacheConfig"; // translate deprecated - cuda2hipRename["cudaFuncCache"] = "hipFuncCache"; - cuda2hipRename["cudaFuncCachePreferNone"] = "hipFuncCachePreferNone"; - cuda2hipRename["cudaFuncCachePreferShared"] = "hipFuncCachePreferShared"; - cuda2hipRename["cudaFuncCachePreferL1"] = "hipFuncCachePreferL1"; - cuda2hipRename["cudaFuncCachePreferEqual"] = "hipFuncCachePreferEqual"; - // function - cuda2hipRename["cudaFuncSetCacheConfig"] = "hipFuncSetCacheConfig"; - - cuda2hipRename["cudaDriverGetVersion"] = "hipDriverGetVersion"; - cuda2hipRename["cudaRuntimeGetVersion"] = "hipRuntimeGetVersion"; - - // Peer2Peer - cuda2hipRename["cudaDeviceCanAccessPeer"] = "hipDeviceCanAccessPeer"; - cuda2hipRename["cudaDeviceDisablePeerAccess"] = "hipDeviceDisablePeerAccess"; - cuda2hipRename["cudaDeviceEnablePeerAccess"] = "hipDeviceEnablePeerAccess"; - cuda2hipRename["cudaMemcpyPeerAsync"] = "hipMemcpyPeerAsync"; - cuda2hipRename["cudaMemcpyPeer"] = "hipMemcpyPeer"; - - // Shared mem: - cuda2hipRename["cudaDeviceSetSharedMemConfig"] = "hipDeviceSetSharedMemConfig"; - cuda2hipRename["cudaThreadSetSharedMemConfig"] = "hipDeviceSetSharedMemConfig"; // translate deprecated - cuda2hipRename["cudaDeviceGetSharedMemConfig"] = "hipDeviceGetSharedMemConfig"; - cuda2hipRename["cudaThreadGetSharedMemConfig"] = "hipDeviceGetSharedMemConfig"; // translate deprecated - cuda2hipRename["cudaSharedMemConfig"] = "hipSharedMemConfig"; - cuda2hipRename["cudaSharedMemBankSizeDefault"] = "hipSharedMemBankSizeDefault"; - cuda2hipRename["cudaSharedMemBankSizeFourByte"] = "hipSharedMemBankSizeFourByte"; - cuda2hipRename["cudaSharedMemBankSizeEightByte"] = "hipSharedMemBankSizeEightByte"; - - cuda2hipRename["cudaGetDeviceCount"] = "hipGetDeviceCount"; - - // Profiler - //cuda2hipRename["cudaProfilerInitialize"] = "hipProfilerInitialize"; // see if these are called anywhere. - cuda2hipRename["cudaProfilerStart"] = "hipProfilerStart"; - cuda2hipRename["cudaProfilerStop"] = "hipProfilerStop"; - - cuda2hipRename["cudaChannelFormatDesc"] = "hipChannelFormatDesc"; - cuda2hipRename["cudaFilterModePoint"] = "hipFilterModePoint"; - cuda2hipRename["cudaReadModeElementType"] = "hipReadModeElementType"; - - cuda2hipRename["cudaCreateChannelDesc"] = "hipCreateChannelDesc"; - cuda2hipRename["cudaBindTexture"] = "hipBindTexture"; - cuda2hipRename["cudaUnbindTexture"] = "hipUnbindTexture"; - } - DenseMap cuda2hipRename; - }; - - StringRef unquoteStr(StringRef s) { - if (s.size() > 1 && s.front() == '"' && s.back() == '"') - return s.substr(1, s.size()-2); - return s; - } - - void processString(StringRef s, struct hipName & map, - Replacements * Replace, SourceManager & SM, SourceLocation start) - { - size_t begin = 0; - while ((begin = s.find("cuda", begin)) != StringRef::npos) { - const size_t end = s.find_first_of(" ", begin + 4); - StringRef name = s.slice(begin, end); - StringRef repName = map.cuda2hipRename[name]; - if (!repName.empty()) { - SourceLocation sl = start.getLocWithOffset(begin + 1); - Replacement Rep(SM, sl, name.size(), repName); - Replace->insert(Rep); - } - if (end == StringRef::npos) break; - begin = end + 1; - } - } - - - struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { - HipifyPPCallbacks(Replacements * R) - : SeenEnd(false), _sm(nullptr), _pp(nullptr), Replace(R) - { - } - - virtual bool handleBeginSource(CompilerInstance &CI, StringRef Filename) override - { - Preprocessor &PP = CI.getPreprocessor(); - SourceManager & SM = CI.getSourceManager(); - setSourceManager(&SM); - PP.addPPCallbacks(std::unique_ptr(this)); - PP.Retain(); - setPreprocessor(&PP); - return true; - } - - virtual void InclusionDirective( - SourceLocation hash_loc, - const Token &include_token, - StringRef file_name, - bool is_angled, - CharSourceRange filename_range, - const FileEntry *file, - StringRef search_path, - StringRef relative_path, - const clang::Module *imported) override - { - if (_sm->isWrittenInMainFile(hash_loc)) { - if (is_angled) { - if (N.cuda2hipRename.count(file_name)) { - std::string repName = N.cuda2hipRename[file_name]; - llvm::errs() << "\nInclude file found: " << file_name << "\n"; - llvm::errs() << "\nSourceLocation:"; filename_range.getBegin().dump(*_sm); - llvm::errs() << "\nWill be replaced with " << repName << "\n"; - SourceLocation sl = filename_range.getBegin(); - SourceLocation sle = filename_range.getEnd(); - const char* B = _sm->getCharacterData(sl); - const char* E = _sm->getCharacterData(sle); - repName = "<" + repName + ">"; - Replacement Rep(*_sm, sl, E - B, repName); - Replace->insert(Rep); - } - } - } - } - - virtual void MacroDefined(const Token &MacroNameTok, - const MacroDirective *MD) override - { - if (_sm->isWrittenInMainFile(MD->getLocation()) && - MD->getKind() == MacroDirective::MD_Define) - { - for (auto T : MD->getMacroInfo()->tokens()) - { - if (T.isAnyIdentifier()) { - StringRef name = T.getIdentifierInfo()->getName(); - if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name]; - llvm::errs() << "\nIdentifier " << name - << " found in definition of macro " - << MacroNameTok.getIdentifierInfo()->getName() << "\n"; - llvm::errs() << "\nwill be replaced with: " << repName << "\n"; - SourceLocation sl = T.getLocation(); - llvm::errs() << "\nSourceLocation: ";sl.dump(*_sm); - llvm::errs() << "\n"; - Replacement Rep(*_sm, sl, name.size(), repName); - Replace->insert(Rep); - } - } - } - } - } - - virtual void MacroExpands(const Token &MacroNameTok, - const MacroDefinition &MD, SourceRange Range, - const MacroArgs *Args) override - { - if (_sm->isWrittenInMainFile(Range.getBegin())) - { - for (unsigned int i = 0; Args && i < MD.getMacroInfo()->getNumArgs(); i++) - { - StringRef macroName = MacroNameTok.getIdentifierInfo()->getName(); - std::vector toks; - // Code below is a kind of stolen from 'MacroArgs::getPreExpArgument' - // to workaround the 'const' MacroArgs passed into this hook. - const Token * start = Args->getUnexpArgument(i); - size_t len = Args->getArgLength(start) + 1; - _pp->EnterTokenStream(ArrayRef(start,len), false); - do { - toks.push_back(Token()); - Token & tk = toks.back(); - _pp->Lex(tk); - } while (toks.back().isNot(tok::eof)); - _pp->RemoveTopOfLexerStack(); - // end of stolen code - for (auto tok : toks) { - if (tok.isAnyIdentifier()) - { - StringRef name = tok.getIdentifierInfo()->getName(); - if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name]; - llvm::errs() << "\nIdentifier " << name - << " found as an actual argument in expansion of macro " - << macroName << "\n"; - llvm::errs() << "\nwill be replaced with: " << repName << "\n"; - SourceLocation sl = tok.getLocation(); - Replacement Rep(*_sm, sl, name.size(), repName); - Replace->insert(Rep); - } - } - if (tok.is(tok::string_literal)) - { - StringRef s(tok.getLiteralData(), tok.getLength()); - processString(unquoteStr(s), N, Replace, *_sm, tok.getLocation()); - } - } - } - } - } - - void EndOfMainFile() override - { - - } - - bool SeenEnd; - void setSourceManager(SourceManager * sm) { _sm = sm; } - void setPreprocessor (Preprocessor * pp) { _pp = pp; } - - private: - - SourceManager * _sm; - Preprocessor * _pp; - - Replacements * Replace; - struct hipName N; - }; - -class Cuda2HipCallback : public MatchFinder::MatchCallback { - public: - Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} - - void run(const MatchFinder::MatchResult &Result) override { - - SourceManager * SM = Result.SourceManager; - - if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) - { - const FunctionDecl * funcDcl = call->getDirectCallee(); - std::string name = funcDcl->getDeclName().getAsString(); - if (N.cuda2hipRename.count(name)) { - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = call->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); - Replace->insert(Rep); - } - } - - if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) - { - LangOptions DefaultLangOptions; - StringRef initialParamList; - SmallString<40> XStr; - raw_svector_ostream OS(XStr); - OS << "hipLaunchParm lp"; - const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); - SourceLocation l1 = kernelDecl->getNameInfo().getLocStart(); - l1.dump(*SM);llvm::outs() << "\n"; - SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(l1, clang::tok::l_paren, *SM, DefaultLangOptions, true); - kernelArgListStart.dump(*SM);llvm::outs() << "\n"; - size_t replacementLength = 0; - if (kernelDecl->getNumParams() > 0) { - const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); - SourceLocation kernelArgListEnd = SourceLocation(pvdLast->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); - replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); - initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); - OS << ", " << initialParamList; - } - - llvm::outs() << "initial paramlist: " << initialParamList << "\n"; - llvm::outs() << "new paramlist: " << OS.str() << "\n"; - Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); - Replace->insert(Rep0); - - XStr.clear(); - OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << kernelDecl->getName() << "), "; - - const CallExpr * config = launchKernel->getConfig(); - llvm::outs() << "\nKernel config arguments:\n"; - for (unsigned argno = 0; argno < config->getNumArgs(); argno++) - { - const Expr * arg = config->getArg(argno); - if (!isa(arg)) { - const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); - - SourceLocation sl(arg->getLocStart()); - SourceLocation el(arg->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); - StringRef outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); - llvm::outs() << "args[ " << argno << "]" << outs << " <" << pvd->getType().getAsString() << ">\n"; - if (pvd->getType().getAsString().compare("dim3") == 0) - OS << " dim3(" << outs << "),"; - else - OS << " " << outs << ","; - } else - OS << " 0,"; - } - - for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) - { - const Expr * arg = launchKernel->getArg(argno); - SourceLocation sl(arg->getLocStart()); - SourceLocation el(arg->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); - std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); - llvm::outs() << outs.c_str() << "\n"; - OS << " " << outs << ","; - } - XStr.pop_back(); - OS << ")"; - size_t length = SM->getCharacterData(clang::Lexer::getLocForEndOfToken(launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - - SM->getCharacterData(launchKernel->getLocStart()); - Replacement Rep(*SM, launchKernel->getLocStart(), length, OS.str()); - Replace->insert(Rep); - } - - if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) - { - if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { - if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { - std::string name = declRef->getDecl()->getNameAsString(); - std::string memberName = threadIdx->getMemberDecl()->getNameAsString(); - size_t pos = memberName.find_first_not_of("__fetch_builtin_"); - memberName = memberName.substr(pos, memberName.length() - pos); - name += "." + memberName; - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = threadIdx->getLocStart(); - Replacement Rep(*SM, sl, name.length(), repName); - Replace->insert(Rep); - } - } - } - - if (const DeclRefExpr * cudaEnumConstantRef = Result.Nodes.getNodeAs("cudaEnumConstantRef")) - { - std::string name = cudaEnumConstantRef->getDecl()->getNameAsString(); - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = cudaEnumConstantRef->getLocStart(); - Replacement Rep(*SM, sl, name.length(), repName); - Replace->insert(Rep); - } - - if (const VarDecl * cudaEnumConstantDecl = Result.Nodes.getNodeAs("cudaEnumConstantDecl")) - { - std::string name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = cudaEnumConstantDecl->getLocStart(); - Replacement Rep(*SM, sl, name.length(), repName); - Replace->insert(Rep); - } - - if (const VarDecl * cudaStructVar = Result.Nodes.getNodeAs("cudaStructVar")) - { - std::string name = - cudaStructVar->getType()->getAsStructureType()->getDecl()->getNameAsString(); - std::string repName = N.cuda2hipRename[name]; - TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.length(), repName); - Replace->insert(Rep); - } - - if (const VarDecl * cudaStructVarPtr = Result.Nodes.getNodeAs("cudaStructVarPtr")) - { - const Type * t = cudaStructVarPtr->getType().getTypePtrOrNull(); - if (t) { - StringRef name = t->getPointeeCXXRecordDecl()->getName(); - StringRef repName = N.cuda2hipRename[name]; - TypeLoc TL = cudaStructVarPtr->getTypeSourceInfo()->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); - } - } - - - if (const ParmVarDecl * cudaParamDecl = Result.Nodes.getNodeAs("cudaParamDecl")) - { - QualType QT = cudaParamDecl->getOriginalType().getUnqualifiedType(); - StringRef name = QT.getAsString(); - const Type * t = QT.getTypePtr(); - if (t->isStructureOrClassType()) { - name = t->getAsCXXRecordDecl()->getName(); - } - StringRef repName = N.cuda2hipRename[name]; - TypeLoc TL = cudaParamDecl->getTypeSourceInfo()->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); - } - - if (const ParmVarDecl * cudaParamDeclPtr = Result.Nodes.getNodeAs("cudaParamDeclPtr")) - { - const Type * pt = cudaParamDeclPtr->getType().getTypePtrOrNull(); - if (pt) { - QualType QT = pt->getPointeeType(); - const Type * t = QT.getTypePtr(); - StringRef name = t->isStructureOrClassType()? - t->getAsCXXRecordDecl()->getName() : StringRef(QT.getAsString()); - StringRef repName = N.cuda2hipRename[name]; - TypeLoc TL = cudaParamDeclPtr->getTypeSourceInfo()->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); - } - } - - - if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) - { - StringRef s = stringLiteral->getString(); - processString(s, N, Replace, *SM, stringLiteral->getLocStart()); - } - - if (const UnaryExprOrTypeTraitExpr * expr = Result.Nodes.getNodeAs("cudaStructSizeOf")) - { - TypeSourceInfo * typeInfo = expr->getArgumentTypeInfo(); - QualType QT = typeInfo->getType().getUnqualifiedType(); - const Type * type = QT.getTypePtr(); - StringRef name = type->getAsCXXRecordDecl()->getName(); - StringRef repName = N.cuda2hipRename[name]; - TypeLoc TL = typeInfo->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); - } - } - - private: - Replacements *Replace; - struct hipName N; -}; - -} // end anonymous namespace - -// Set up the command line options -static cl::OptionCategory ToolTemplateCategory("CUDA to HIP source translator options"); -static cl::extrahelp MoreHelp( " specify the path of source file\n\n" ); -static cl::opt -OutputFilename("o", cl::desc("Output filename"), cl::value_desc("filename"), cl::cat(ToolTemplateCategory)); - -int main(int argc, const char **argv) { - - llvm::sys::PrintStackTraceOnErrorSignal(); - - int Result; - - CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory, llvm::cl::Required); - std::string dst = OutputFilename; - std::vector fileSources = OptionsParser.getSourcePathList(); - if (dst.empty()) { - dst = fileSources[0]; - size_t pos = dst.find(".cu"); - if (pos != std::string::npos) { - dst = dst.substr(0, pos) + ".hip.cu"; - } else { - llvm::errs() << "Input .cu file was not specified.\n"; - return 1; - } - } else { - dst += ".cu"; - } - std::ifstream source(fileSources[0], std::ios::binary); - std::ofstream dest(dst, std::ios::binary); - dest << source.rdbuf(); - source.close(); - dest.close(); - - RefactoringTool Tool(OptionsParser.getCompilations(), dst); - ast_matchers::MatchFinder Finder; - Cuda2HipCallback Callback(&Tool.getReplacements()); - HipifyPPCallbacks PPCallbacks(&Tool.getReplacements()); - Finder.addMatcher(callExpr(isExpansionInMainFile(), callee(functionDecl(matchesName("cuda.*")))).bind("cudaCall"), &Callback); - Finder.addMatcher(cudaKernelCallExpr().bind("cudaLaunchKernel"), &Callback); - Finder.addMatcher(memberExpr(isExpansionInMainFile(), hasObjectExpression(hasType(cxxRecordDecl(matchesName("__cuda_builtin_"))))).bind("cudaBuiltin"), &Callback); - Finder.addMatcher(declRefExpr(isExpansionInMainFile(), to(enumConstantDecl(matchesName("cuda.*")))).bind("cudaEnumConstantRef"), &Callback); - Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))).bind("cudaEnumConstantDecl"), &Callback); - Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); - Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(pointsTo(cxxRecordDecl(matchesName("cuda.*"))))).bind("cudaStructVarPtr"), &Callback); - Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); - Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(pointsTo(namedDecl(matchesName("cuda.*"))))).bind("cudaParamDeclPtr"), &Callback); - Finder.addMatcher(expr(sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration(cxxRecordDecl(matchesName("cuda.*"))))))).bind("cudaStructSizeOf"), &Callback); - Finder.addMatcher(stringLiteral().bind("stringLiteral"), &Callback); - - auto action = newFrontendActionFactory(&Finder, &PPCallbacks); - - std::vector compilationStages; - compilationStages.push_back("--cuda-host-only"); - compilationStages.push_back("--cuda-device-only"); - - for (auto Stage : compilationStages) - { - Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster(Stage, ArgumentInsertPosition::BEGIN)); - Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster("-std=c++11")); - Tool.appendArgumentsAdjuster(getClangSyntaxOnlyAdjuster()); - Result = Tool.run(action.get()); - - Tool.clearArgumentsAdjusters(); - } - - LangOptions DefaultLangOptions; - IntrusiveRefCntPtr DiagOpts = new DiagnosticOptions(); - TextDiagnosticPrinter DiagnosticPrinter(llvm::errs(), &*DiagOpts); - DiagnosticsEngine Diagnostics( - IntrusiveRefCntPtr(new DiagnosticIDs()), - &*DiagOpts, &DiagnosticPrinter, false); - SourceManager Sources(Diagnostics, Tool.getFiles()); - - llvm::outs() << "Replacements collected by the tool:\n"; - for (auto &r : Tool.getReplacements()) { - llvm::outs() << r.toString() << "\n"; - } - - Rewriter Rewrite(Sources, DefaultLangOptions); - - if (!Tool.applyAllReplacements(Rewrite)) { - llvm::errs() << "Skipped some replacements.\n"; - } - - Result = Rewrite.overwriteChangedFiles(); - - - { - size_t pos = dst.find(".cu"); - if (pos != std::string::npos) - { - rename(dst.c_str(), dst.substr(0, pos).c_str()); - } - } - return Result; -} +/* +Copyright (c) 2015-2016 Advanced Micro Devices, Inc. All rights reserved. + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. +*/ +/** + * @file Cuda2Hip.cpp + * + * This file is compiled and linked into clang based hipify tool. + */ +#include "clang/ASTMatchers/ASTMatchers.h" +#include "clang/ASTMatchers/ASTMatchFinder.h" +#include "clang/Basic/SourceManager.h" +#include "clang/Frontend/FrontendActions.h" +#include "clang/Lex/Lexer.h" +#include "clang/Tooling/CommonOptionsParser.h" +#include "clang/Tooling/Refactoring.h" +#include "clang/Tooling/Tooling.h" +#include "llvm/Support/CommandLine.h" +#include "llvm/Support/MemoryBuffer.h" +#include "llvm/Support/Signals.h" +#include "llvm/Support/Debug.h" +#include "clang/Frontend/TextDiagnosticPrinter.h" +#include "clang/Rewrite/Core/Rewriter.h" +#include "clang/Lex/MacroInfo.h" +#include "clang/Frontend/CompilerInstance.h" +#include "clang/Lex/Preprocessor.h" +#include "clang/Lex/PPCallbacks.h" +#include "clang/Lex/MacroArgs.h" + +#include +#include + +using namespace clang; +using namespace clang::ast_matchers; +using namespace clang::tooling; +using namespace llvm; + +#define DEBUG_TYPE "cuda2hip" + +namespace { + struct hipName { + hipName() { + // defines + cuda2hipRename["__CUDACC__"] = "__HIPCC__"; + + // includes + cuda2hipRename["cuda_runtime.h"] = "hip_runtime.h"; + cuda2hipRename["cuda_runtime_api.h"] = "hip_runtime_api.h"; + + // Error codes and return types: + cuda2hipRename["cudaError_t"] = "hipError_t"; + cuda2hipRename["cudaError"] = "hipError"; + cuda2hipRename["cudaSuccess"] = "hipSuccess"; + + cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; + cuda2hipRename["cudaErrorMemoryAllocation"] = "hipErrorMemoryAllocation"; + cuda2hipRename["cudaErrorMemoryFree"] = "hipErrorMemoryFree"; + cuda2hipRename["cudaErrorUnknownSymbol"] = "hipErrorUnknownSymbol"; + cuda2hipRename["cudaErrorOutOfResources"] = "hipErrorOutOfResources"; + cuda2hipRename["cudaErrorInvalidValue"] = "hipErrorInvalidValue"; + cuda2hipRename["cudaErrorInvalidResourceHandle"] = "hipErrorInvalidResourceHandle"; + cuda2hipRename["cudaErrorInvalidDevice"] = "hipErrorInvalidDevice"; + cuda2hipRename["cudaErrorNoDevice"] = "hipErrorNoDevice"; + cuda2hipRename["cudaErrorNotReady"] = "hipErrorNotReady"; + cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; + + // error APIs: + cuda2hipRename["cudaGetLastError"] = "hipGetLastError"; + cuda2hipRename["cudaPeekAtLastError"] = "hipPeekAtLastError"; + cuda2hipRename["cudaGetErrorName"] = "hipGetErrorName"; + cuda2hipRename["cudaGetErrorString"] = "hipGetErrorString"; + + // Memcpy + cuda2hipRename["cudaMemcpy"] = "hipMemcpy"; + cuda2hipRename["cudaMemcpyHostToHost"] = "hipMemcpyHostToHost"; + cuda2hipRename["cudaMemcpyHostToDevice"] = "hipMemcpyHostToDevice"; + cuda2hipRename["cudaMemcpyDeviceToHost"] = "hipMemcpyDeviceToHost"; + cuda2hipRename["cudaMemcpyDeviceToDevice"] = "hipMemcpyDeviceToDevice"; + cuda2hipRename["cudaMemcpyDefault"] = "hipMemcpyDefault"; + cuda2hipRename["cudaMemcpyToSymbol"] = "hipMemcpyToSymbol"; + cuda2hipRename["cudaMemset"] = "hipMemset"; + cuda2hipRename["cudaMemsetAsync"] = "hipMemsetAsync"; + cuda2hipRename["cudaMemcpyAsync"] = "hipMemcpyAsync"; + cuda2hipRename["cudaMemGetInfo"] = "hipMemGetInfo"; + cuda2hipRename["cudaMemcpyKind"] = "hipMemcpyKind"; + + // Memory management : + cuda2hipRename["cudaMalloc"] = "hipMalloc"; + cuda2hipRename["cudaMallocHost"] = "hipMallocHost"; + cuda2hipRename["cudaFree"] = "hipFree"; + cuda2hipRename["cudaFreeHost"] = "hipFreeHost"; + + // Coordinate Indexing and Dimensions: + cuda2hipRename["threadIdx.x"] = "hipThreadIdx_x"; + cuda2hipRename["threadIdx.y"] = "hipThreadIdx_y"; + cuda2hipRename["threadIdx.z"] = "hipThreadIdx_z"; + + cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; + cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; + cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; + + cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; + cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; + cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; + + cuda2hipRename["gridDim.x"] = "hipGridDim_x"; + cuda2hipRename["gridDim.y"] = "hipGridDim_y"; + cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + + cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; + cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; + cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; + + cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; + cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; + cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; + + cuda2hipRename["gridDim.x"] = "hipGridDim_x"; + cuda2hipRename["gridDim.y"] = "hipGridDim_y"; + cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + + + cuda2hipRename["warpSize"] = "hipWarpSize"; + + // Events + cuda2hipRename["cudaEvent_t"] = "hipEvent_t"; + cuda2hipRename["cudaEventCreate"] = "hipEventCreate"; + cuda2hipRename["cudaEventCreateWithFlags"] = "hipEventCreateWithFlags"; + cuda2hipRename["cudaEventDestroy"] = "hipEventDestroy"; + cuda2hipRename["cudaEventRecord"] = "hipEventRecord"; + cuda2hipRename["cudaEventElapsedTime"] = "hipEventElapsedTime"; + cuda2hipRename["cudaEventSynchronize"] = "hipEventSynchronize"; + + // Streams + cuda2hipRename["cudaStream_t"] = "hipStream_t"; + cuda2hipRename["cudaStreamCreate"] = "hipStreamCreate"; + cuda2hipRename["cudaStreamCreateWithFlags"] = "hipStreamCreateWithFlags"; + cuda2hipRename["cudaStreamDestroy"] = "hipStreamDestroy"; + cuda2hipRename["cudaStreamWaitEvent"] = "hipStreamWaitEven"; + cuda2hipRename["cudaStreamSynchronize"] = "hipStreamSynchronize"; + cuda2hipRename["cudaStreamDefault"] = "hipStreamDefault"; + cuda2hipRename["cudaStreamNonBlocking"] = "hipStreamNonBlocking"; + + // Other synchronization + cuda2hipRename["cudaDeviceSynchronize"] = "hipDeviceSynchronize"; + cuda2hipRename["cudaThreadSynchronize"] = "hipDeviceSynchronize"; // translate deprecated cudaThreadSynchronize + cuda2hipRename["cudaDeviceReset"] = "hipDeviceReset"; + cuda2hipRename["cudaThreadExit"] = "hipDeviceReset"; // translate deprecated cudaThreadExit + cuda2hipRename["cudaSetDevice"] = "hipSetDevice"; + cuda2hipRename["cudaGetDevice"] = "hipGetDevice"; + + // Device + cuda2hipRename["cudaDeviceProp"] = "hipDeviceProp_t"; + cuda2hipRename["cudaGetDeviceProperties"] = "hipDeviceGetProperties"; + + // Cache config + cuda2hipRename["cudaDeviceSetCacheConfig"] = "hipDeviceSetCacheConfig"; + cuda2hipRename["cudaThreadSetCacheConfig"] = "hipDeviceSetCacheConfig"; // translate deprecated + cuda2hipRename["cudaDeviceGetCacheConfig"] = "hipDeviceGetCacheConfig"; + cuda2hipRename["cudaThreadGetCacheConfig"] = "hipDeviceGetCacheConfig"; // translate deprecated + cuda2hipRename["cudaFuncCache"] = "hipFuncCache"; + cuda2hipRename["cudaFuncCachePreferNone"] = "hipFuncCachePreferNone"; + cuda2hipRename["cudaFuncCachePreferShared"] = "hipFuncCachePreferShared"; + cuda2hipRename["cudaFuncCachePreferL1"] = "hipFuncCachePreferL1"; + cuda2hipRename["cudaFuncCachePreferEqual"] = "hipFuncCachePreferEqual"; + // function + cuda2hipRename["cudaFuncSetCacheConfig"] = "hipFuncSetCacheConfig"; + + cuda2hipRename["cudaDriverGetVersion"] = "hipDriverGetVersion"; + cuda2hipRename["cudaRuntimeGetVersion"] = "hipRuntimeGetVersion"; + + // Peer2Peer + cuda2hipRename["cudaDeviceCanAccessPeer"] = "hipDeviceCanAccessPeer"; + cuda2hipRename["cudaDeviceDisablePeerAccess"] = "hipDeviceDisablePeerAccess"; + cuda2hipRename["cudaDeviceEnablePeerAccess"] = "hipDeviceEnablePeerAccess"; + cuda2hipRename["cudaMemcpyPeerAsync"] = "hipMemcpyPeerAsync"; + cuda2hipRename["cudaMemcpyPeer"] = "hipMemcpyPeer"; + + // Shared mem: + cuda2hipRename["cudaDeviceSetSharedMemConfig"] = "hipDeviceSetSharedMemConfig"; + cuda2hipRename["cudaThreadSetSharedMemConfig"] = "hipDeviceSetSharedMemConfig"; // translate deprecated + cuda2hipRename["cudaDeviceGetSharedMemConfig"] = "hipDeviceGetSharedMemConfig"; + cuda2hipRename["cudaThreadGetSharedMemConfig"] = "hipDeviceGetSharedMemConfig"; // translate deprecated + cuda2hipRename["cudaSharedMemConfig"] = "hipSharedMemConfig"; + cuda2hipRename["cudaSharedMemBankSizeDefault"] = "hipSharedMemBankSizeDefault"; + cuda2hipRename["cudaSharedMemBankSizeFourByte"] = "hipSharedMemBankSizeFourByte"; + cuda2hipRename["cudaSharedMemBankSizeEightByte"] = "hipSharedMemBankSizeEightByte"; + + cuda2hipRename["cudaGetDeviceCount"] = "hipGetDeviceCount"; + + // Profiler + //cuda2hipRename["cudaProfilerInitialize"] = "hipProfilerInitialize"; // see if these are called anywhere. + cuda2hipRename["cudaProfilerStart"] = "hipProfilerStart"; + cuda2hipRename["cudaProfilerStop"] = "hipProfilerStop"; + + cuda2hipRename["cudaChannelFormatDesc"] = "hipChannelFormatDesc"; + cuda2hipRename["cudaFilterModePoint"] = "hipFilterModePoint"; + cuda2hipRename["cudaReadModeElementType"] = "hipReadModeElementType"; + + cuda2hipRename["cudaCreateChannelDesc"] = "hipCreateChannelDesc"; + cuda2hipRename["cudaBindTexture"] = "hipBindTexture"; + cuda2hipRename["cudaUnbindTexture"] = "hipUnbindTexture"; + } + DenseMap cuda2hipRename; + }; + + StringRef unquoteStr(StringRef s) { + if (s.size() > 1 && s.front() == '"' && s.back() == '"') + return s.substr(1, s.size()-2); + return s; + } + + void processString(StringRef s, struct hipName & map, + Replacements * Replace, SourceManager & SM, SourceLocation start) + { + size_t begin = 0; + while ((begin = s.find("cuda", begin)) != StringRef::npos) { + const size_t end = s.find_first_of(" ", begin + 4); + StringRef name = s.slice(begin, end); + StringRef repName = map.cuda2hipRename[name]; + if (!repName.empty()) { + SourceLocation sl = start.getLocWithOffset(begin + 1); + Replacement Rep(SM, sl, name.size(), repName); + Replace->insert(Rep); + } + if (end == StringRef::npos) break; + begin = end + 1; + } + } + + + struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { + HipifyPPCallbacks(Replacements * R) + : SeenEnd(false), _sm(nullptr), _pp(nullptr), Replace(R) + { + } + + virtual bool handleBeginSource(CompilerInstance &CI, StringRef Filename) override + { + Preprocessor &PP = CI.getPreprocessor(); + SourceManager & SM = CI.getSourceManager(); + setSourceManager(&SM); + PP.addPPCallbacks(std::unique_ptr(this)); + PP.Retain(); + setPreprocessor(&PP); + return true; + } + + virtual void InclusionDirective( + SourceLocation hash_loc, + const Token &include_token, + StringRef file_name, + bool is_angled, + CharSourceRange filename_range, + const FileEntry *file, + StringRef search_path, + StringRef relative_path, + const clang::Module *imported) override + { + if (_sm->isWrittenInMainFile(hash_loc)) { + if (is_angled) { + if (N.cuda2hipRename.count(file_name)) { + std::string repName = N.cuda2hipRename[file_name]; + llvm::errs() << "\nInclude file found: " << file_name << "\n"; + llvm::errs() << "\nSourceLocation:"; filename_range.getBegin().dump(*_sm); + llvm::errs() << "\nWill be replaced with " << repName << "\n"; + SourceLocation sl = filename_range.getBegin(); + SourceLocation sle = filename_range.getEnd(); + const char* B = _sm->getCharacterData(sl); + const char* E = _sm->getCharacterData(sle); + repName = "<" + repName + ">"; + Replacement Rep(*_sm, sl, E - B, repName); + Replace->insert(Rep); + } + } + } + } + + virtual void MacroDefined(const Token &MacroNameTok, + const MacroDirective *MD) override + { + if (_sm->isWrittenInMainFile(MD->getLocation()) && + MD->getKind() == MacroDirective::MD_Define) + { + for (auto T : MD->getMacroInfo()->tokens()) + { + if (T.isAnyIdentifier()) { + StringRef name = T.getIdentifierInfo()->getName(); + if (N.cuda2hipRename.count(name)) { + StringRef repName = N.cuda2hipRename[name]; + llvm::errs() << "\nIdentifier " << name + << " found in definition of macro " + << MacroNameTok.getIdentifierInfo()->getName() << "\n"; + llvm::errs() << "\nwill be replaced with: " << repName << "\n"; + SourceLocation sl = T.getLocation(); + llvm::errs() << "\nSourceLocation: ";sl.dump(*_sm); + llvm::errs() << "\n"; + Replacement Rep(*_sm, sl, name.size(), repName); + Replace->insert(Rep); + } + } + } + } + } + + virtual void MacroExpands(const Token &MacroNameTok, + const MacroDefinition &MD, SourceRange Range, + const MacroArgs *Args) override + { + if (_sm->isWrittenInMainFile(Range.getBegin())) + { + for (unsigned int i = 0; Args && i < MD.getMacroInfo()->getNumArgs(); i++) + { + StringRef macroName = MacroNameTok.getIdentifierInfo()->getName(); + std::vector toks; + // Code below is a kind of stolen from 'MacroArgs::getPreExpArgument' + // to workaround the 'const' MacroArgs passed into this hook. + const Token * start = Args->getUnexpArgument(i); + size_t len = Args->getArgLength(start) + 1; + _pp->EnterTokenStream(ArrayRef(start,len), false); + do { + toks.push_back(Token()); + Token & tk = toks.back(); + _pp->Lex(tk); + } while (toks.back().isNot(tok::eof)); + _pp->RemoveTopOfLexerStack(); + // end of stolen code + for (auto tok : toks) { + if (tok.isAnyIdentifier()) + { + StringRef name = tok.getIdentifierInfo()->getName(); + if (N.cuda2hipRename.count(name)) { + StringRef repName = N.cuda2hipRename[name]; + llvm::errs() << "\nIdentifier " << name + << " found as an actual argument in expansion of macro " + << macroName << "\n"; + llvm::errs() << "\nwill be replaced with: " << repName << "\n"; + SourceLocation sl = tok.getLocation(); + Replacement Rep(*_sm, sl, name.size(), repName); + Replace->insert(Rep); + } + } + if (tok.is(tok::string_literal)) + { + StringRef s(tok.getLiteralData(), tok.getLength()); + processString(unquoteStr(s), N, Replace, *_sm, tok.getLocation()); + } + } + } + } + } + + void EndOfMainFile() override + { + + } + + bool SeenEnd; + void setSourceManager(SourceManager * sm) { _sm = sm; } + void setPreprocessor (Preprocessor * pp) { _pp = pp; } + + private: + + SourceManager * _sm; + Preprocessor * _pp; + + Replacements * Replace; + struct hipName N; + }; + +class Cuda2HipCallback : public MatchFinder::MatchCallback { + public: + Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} + + void run(const MatchFinder::MatchResult &Result) override { + + SourceManager * SM = Result.SourceManager; + + if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) + { + const FunctionDecl * funcDcl = call->getDirectCallee(); + std::string name = funcDcl->getDeclName().getAsString(); + if (N.cuda2hipRename.count(name)) { + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = call->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); + } + } + + if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) + { + LangOptions DefaultLangOptions; + StringRef initialParamList; + SmallString<40> XStr; + raw_svector_ostream OS(XStr); + OS << "hipLaunchParm lp"; + const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); + SourceLocation l1 = kernelDecl->getNameInfo().getLocStart(); + l1.dump(*SM);llvm::outs() << "\n"; + SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(l1, clang::tok::l_paren, *SM, DefaultLangOptions, true); + kernelArgListStart.dump(*SM);llvm::outs() << "\n"; + size_t replacementLength = 0; + if (kernelDecl->getNumParams() > 0) { + const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); + SourceLocation kernelArgListEnd = SourceLocation(pvdLast->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); + replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); + initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); + OS << ", " << initialParamList; + } + + llvm::outs() << "initial paramlist: " << initialParamList << "\n"; + llvm::outs() << "new paramlist: " << OS.str() << "\n"; + Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); + Replace->insert(Rep0); + + XStr.clear(); + OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << kernelDecl->getName() << "), "; + + const CallExpr * config = launchKernel->getConfig(); + llvm::outs() << "\nKernel config arguments:\n"; + for (unsigned argno = 0; argno < config->getNumArgs(); argno++) + { + const Expr * arg = config->getArg(argno); + if (!isa(arg)) { + const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); + + SourceLocation sl(arg->getLocStart()); + SourceLocation el(arg->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + StringRef outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + llvm::outs() << "args[ " << argno << "]" << outs << " <" << pvd->getType().getAsString() << ">\n"; + if (pvd->getType().getAsString().compare("dim3") == 0) + OS << " dim3(" << outs << "),"; + else + OS << " " << outs << ","; + } else + OS << " 0,"; + } + + for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) + { + const Expr * arg = launchKernel->getArg(argno); + SourceLocation sl(arg->getLocStart()); + SourceLocation el(arg->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + llvm::outs() << outs.c_str() << "\n"; + OS << " " << outs << ","; + } + XStr.pop_back(); + OS << ")"; + size_t length = SM->getCharacterData(clang::Lexer::getLocForEndOfToken(launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - + SM->getCharacterData(launchKernel->getLocStart()); + Replacement Rep(*SM, launchKernel->getLocStart(), length, OS.str()); + Replace->insert(Rep); + } + + if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) + { + if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { + if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { + std::string name = declRef->getDecl()->getNameAsString(); + std::string memberName = threadIdx->getMemberDecl()->getNameAsString(); + size_t pos = memberName.find_first_not_of("__fetch_builtin_"); + memberName = memberName.substr(pos, memberName.length() - pos); + name += "." + memberName; + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = threadIdx->getLocStart(); + Replacement Rep(*SM, sl, name.length(), repName); + Replace->insert(Rep); + } + } + } + + if (const DeclRefExpr * cudaEnumConstantRef = Result.Nodes.getNodeAs("cudaEnumConstantRef")) + { + std::string name = cudaEnumConstantRef->getDecl()->getNameAsString(); + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = cudaEnumConstantRef->getLocStart(); + Replacement Rep(*SM, sl, name.length(), repName); + Replace->insert(Rep); + } + + if (const VarDecl * cudaEnumConstantDecl = Result.Nodes.getNodeAs("cudaEnumConstantDecl")) + { + std::string name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = cudaEnumConstantDecl->getLocStart(); + Replacement Rep(*SM, sl, name.length(), repName); + Replace->insert(Rep); + } + + if (const VarDecl * cudaStructVar = Result.Nodes.getNodeAs("cudaStructVar")) + { + std::string name = + cudaStructVar->getType()->getAsStructureType()->getDecl()->getNameAsString(); + std::string repName = N.cuda2hipRename[name]; + TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.length(), repName); + Replace->insert(Rep); + } + + if (const VarDecl * cudaStructVarPtr = Result.Nodes.getNodeAs("cudaStructVarPtr")) + { + const Type * t = cudaStructVarPtr->getType().getTypePtrOrNull(); + if (t) { + StringRef name = t->getPointeeCXXRecordDecl()->getName(); + StringRef repName = N.cuda2hipRename[name]; + TypeLoc TL = cudaStructVarPtr->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } + } + + + if (const ParmVarDecl * cudaParamDecl = Result.Nodes.getNodeAs("cudaParamDecl")) + { + QualType QT = cudaParamDecl->getOriginalType().getUnqualifiedType(); + StringRef name = QT.getAsString(); + const Type * t = QT.getTypePtr(); + if (t->isStructureOrClassType()) { + name = t->getAsCXXRecordDecl()->getName(); + } + StringRef repName = N.cuda2hipRename[name]; + TypeLoc TL = cudaParamDecl->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } + + if (const ParmVarDecl * cudaParamDeclPtr = Result.Nodes.getNodeAs("cudaParamDeclPtr")) + { + const Type * pt = cudaParamDeclPtr->getType().getTypePtrOrNull(); + if (pt) { + QualType QT = pt->getPointeeType(); + const Type * t = QT.getTypePtr(); + StringRef name = t->isStructureOrClassType()? + t->getAsCXXRecordDecl()->getName() : StringRef(QT.getAsString()); + StringRef repName = N.cuda2hipRename[name]; + TypeLoc TL = cudaParamDeclPtr->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } + } + + + if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) + { + StringRef s = stringLiteral->getString(); + processString(s, N, Replace, *SM, stringLiteral->getLocStart()); + } + + if (const UnaryExprOrTypeTraitExpr * expr = Result.Nodes.getNodeAs("cudaStructSizeOf")) + { + TypeSourceInfo * typeInfo = expr->getArgumentTypeInfo(); + QualType QT = typeInfo->getType().getUnqualifiedType(); + const Type * type = QT.getTypePtr(); + StringRef name = type->getAsCXXRecordDecl()->getName(); + StringRef repName = N.cuda2hipRename[name]; + TypeLoc TL = typeInfo->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } + } + + private: + Replacements *Replace; + struct hipName N; +}; + +} // end anonymous namespace + +// Set up the command line options +static cl::OptionCategory ToolTemplateCategory("CUDA to HIP source translator options"); +static cl::extrahelp MoreHelp( " specify the path of source file\n\n" ); +static cl::opt +OutputFilename("o", cl::desc("Output filename"), cl::value_desc("filename"), cl::cat(ToolTemplateCategory)); + +int main(int argc, const char **argv) { + + llvm::sys::PrintStackTraceOnErrorSignal(); + + int Result; + + CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory, llvm::cl::Required); + std::string dst = OutputFilename; + std::vector fileSources = OptionsParser.getSourcePathList(); + if (dst.empty()) { + dst = fileSources[0]; + size_t pos = dst.find(".cu"); + if (pos != std::string::npos) { + dst = dst.substr(0, pos) + ".hip.cu"; + } else { + llvm::errs() << "Input .cu file was not specified.\n"; + return 1; + } + } else { + dst += ".cu"; + } + std::ifstream source(fileSources[0], std::ios::binary); + std::ofstream dest(dst, std::ios::binary); + dest << source.rdbuf(); + source.close(); + dest.close(); + + RefactoringTool Tool(OptionsParser.getCompilations(), dst); + ast_matchers::MatchFinder Finder; + Cuda2HipCallback Callback(&Tool.getReplacements()); + HipifyPPCallbacks PPCallbacks(&Tool.getReplacements()); + Finder.addMatcher(callExpr(isExpansionInMainFile(), callee(functionDecl(matchesName("cuda.*")))).bind("cudaCall"), &Callback); + Finder.addMatcher(cudaKernelCallExpr().bind("cudaLaunchKernel"), &Callback); + Finder.addMatcher(memberExpr(isExpansionInMainFile(), hasObjectExpression(hasType(cxxRecordDecl(matchesName("__cuda_builtin_"))))).bind("cudaBuiltin"), &Callback); + Finder.addMatcher(declRefExpr(isExpansionInMainFile(), to(enumConstantDecl(matchesName("cuda.*")))).bind("cudaEnumConstantRef"), &Callback); + Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))).bind("cudaEnumConstantDecl"), &Callback); + Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); + Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(pointsTo(cxxRecordDecl(matchesName("cuda.*"))))).bind("cudaStructVarPtr"), &Callback); + Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); + Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(pointsTo(namedDecl(matchesName("cuda.*"))))).bind("cudaParamDeclPtr"), &Callback); + Finder.addMatcher(expr(sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration(cxxRecordDecl(matchesName("cuda.*"))))))).bind("cudaStructSizeOf"), &Callback); + Finder.addMatcher(stringLiteral().bind("stringLiteral"), &Callback); + + auto action = newFrontendActionFactory(&Finder, &PPCallbacks); + + std::vector compilationStages; + compilationStages.push_back("--cuda-host-only"); + compilationStages.push_back("--cuda-device-only"); + + for (auto Stage : compilationStages) + { + Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster(Stage, ArgumentInsertPosition::BEGIN)); + Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster("-std=c++11")); + Tool.appendArgumentsAdjuster(getClangSyntaxOnlyAdjuster()); + Result = Tool.run(action.get()); + + Tool.clearArgumentsAdjusters(); + } + + LangOptions DefaultLangOptions; + IntrusiveRefCntPtr DiagOpts = new DiagnosticOptions(); + TextDiagnosticPrinter DiagnosticPrinter(llvm::errs(), &*DiagOpts); + DiagnosticsEngine Diagnostics( + IntrusiveRefCntPtr(new DiagnosticIDs()), + &*DiagOpts, &DiagnosticPrinter, false); + SourceManager Sources(Diagnostics, Tool.getFiles()); + + llvm::outs() << "Replacements collected by the tool:\n"; + for (auto &r : Tool.getReplacements()) { + llvm::outs() << r.toString() << "\n"; + } + + Rewriter Rewrite(Sources, DefaultLangOptions); + + if (!Tool.applyAllReplacements(Rewrite)) { + llvm::errs() << "Skipped some replacements.\n"; + } + + Result = Rewrite.overwriteChangedFiles(); + + + { + size_t pos = dst.find(".cu"); + if (pos != std::string::npos) + { + rename(dst.c_str(), dst.substr(0, pos).c_str()); + } + } + return Result; +} From b90ee96510490cd4fcbf067ce687626a98eae155 Mon Sep 17 00:00:00 2001 From: Daniil Fukalov Date: Wed, 2 Mar 2016 20:05:42 +0300 Subject: [PATCH 22/56] Update README.md --- hipamd/README.md | 32 ++++++++++++++++---------------- 1 file changed, 16 insertions(+), 16 deletions(-) diff --git a/hipamd/README.md b/hipamd/README.md index a3725394ad..0ddd4f9b91 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -1,6 +1,22 @@ # HIPIFY The CLANG-based HIPIFY tool - translates CUDA to [HIP](https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP/blob/master/README.md) +# How to Build tool *in llvm source tree* +- get LLVM, CLANG and clang-tools-extra sources +- put hipify folder into llvm/tools/clang/tools/extra, add it to llvm/tools/clang/tools/extra/CMakeLists.txt +- run cmake and build tool +``` +git clone http://llvm.org/git/llvm.git llvm +git clone http://llvm.org/git/clang.git llvm/tools/clang +git clone http://llvm.org/git/clang-tools-extra.git llvm/tools/clang/tools/extra +git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git llvm/tools/clang/tools/extra/hipify +echo "add_subdirectory(hipify)" >> llvm/tools/clang/tools/extra/CMakeLists.txt + +mkdir llvm_build && cd llvm_build +cmake -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm +make +``` + # How to Build *standalone* tool - Get LLVM and CLANG sources, build them and install to a **LLVM_INSTALL_PATH** folder - mkdir for hipify, run cmake there and build the tool: @@ -18,22 +34,6 @@ cmake -DLLVM_DIR="LLVM_INSTALL_PATH" -DHIPIFY_STANDLONE=1 .. make ``` -# How to Build tool *in llvm source tree* -- get LLVM, CLANG and clang-tools-extra sources -- put hipify folder into llvm/tools/clang/tools/extra, add it to llvm/tools/clang/tools/extra/CMakeLists.txt -- run cmake and build tool -``` -git clone http://llvm.org/git/llvm.git llvm -git clone http://llvm.org/git/clang.git llvm/tools/clang -git clone http://llvm.org/git/clang-tools-extra.git llvm/tools/clang/tools/extra -git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git llvm/tools/clang/tools/extra/hipify -echo "add_subdirectory(hipify)" >> llvm/tools/clang/tools/extra/CMakeLists.txt - -mkdir llvm_build && cd llvm_build -cmake -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm -make -C tools/clang/tools/extra/hipify -``` - # How to run tests (for *standalone* tool only) - install Python and add python-setuptools - install lit python script From 5db0984077f6708b992fe4d7dd20e9660bef9b16 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Thu, 3 Mar 2016 18:28:24 +0300 Subject: [PATCH 23/56] 1. fixed file extension search bug 2. added new dependency --- hipamd/CMakeLists.txt | 1 + hipamd/src/Cuda2Hip.cpp | 13 +++++-------- 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 3348056faf..0c209b8fa2 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -41,6 +41,7 @@ target_link_libraries(hipify clangToolingCore clangRewrite clangBasic + LLVMProfileData LLVMSupport LLVMMCParser LLVMMC diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 42d3ca836f..129b47e63e 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -611,7 +611,7 @@ int main(int argc, const char **argv) { std::vector fileSources = OptionsParser.getSourcePathList(); if (dst.empty()) { dst = fileSources[0]; - size_t pos = dst.find(".cu"); + size_t pos = dst.rfind(".cu"); if (pos != std::string::npos) { dst = dst.substr(0, pos) + ".hip.cu"; } else { @@ -656,7 +656,7 @@ int main(int argc, const char **argv) { Tool.appendArgumentsAdjuster(getClangSyntaxOnlyAdjuster()); Result = Tool.run(action.get()); - Tool.clearArgumentsAdjusters(); + Tool.clearArgumentsAdjusters(); } LangOptions DefaultLangOptions; @@ -680,13 +680,10 @@ int main(int argc, const char **argv) { Result = Rewrite.overwriteChangedFiles(); - + size_t pos = dst.rfind(".cu"); + if (pos != std::string::npos) { - size_t pos = dst.find(".cu"); - if (pos != std::string::npos) - { - rename(dst.c_str(), dst.substr(0, pos).c_str()); - } + rename(dst.c_str(), dst.substr(0, pos).c_str()); } return Result; } From 7249e26c703ac69c79dff733acecea47d5d88338 Mon Sep 17 00:00:00 2001 From: atimofee Date: Thu, 3 Mar 2016 19:36:52 +0300 Subject: [PATCH 24/56] Assert ("This function is used in places that assume strings use char") in stringLiteral::getString() FIXED --- hipamd/src/Cuda2Hip.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 42d3ca836f..f27a1bc1e5 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -569,8 +569,10 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) { - StringRef s = stringLiteral->getString(); - processString(s, N, Replace, *SM, stringLiteral->getLocStart()); + if (stringLiteral->getCharByteWidth() == 1) { + StringRef s = stringLiteral->getString(); + processString(s, N, Replace, *SM, stringLiteral->getLocStart()); + } } if (const UnaryExprOrTypeTraitExpr * expr = Result.Nodes.getNodeAs("cudaStructSizeOf")) From 236c38719c04d10becb7b60e5508756f3f091bfa Mon Sep 17 00:00:00 2001 From: atimofee Date: Fri, 4 Mar 2016 22:07:41 +0300 Subject: [PATCH 25/56] Template kernels calls and declaration conversion added --- hipamd/src/Cuda2Hip.cpp | 96 +++++++++++++++++++++++++++-------------- 1 file changed, 63 insertions(+), 33 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index f2a18262a9..434d74e584 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -324,7 +324,7 @@ namespace { const MacroDefinition &MD, SourceRange Range, const MacroArgs *Args) override { - if (_sm->isWrittenInMainFile(Range.getBegin())) + if (_sm->isWrittenInMainFile(MacroNameTok.getLocation())) { for (unsigned int i = 0; Args && i < MD.getMacroInfo()->getNumArgs(); i++) { @@ -386,12 +386,43 @@ namespace { }; class Cuda2HipCallback : public MatchFinder::MatchCallback { - public: - Cuda2HipCallback(Replacements *Replace) : Replace(Replace) {} + public: + Cuda2HipCallback(Replacements *Replace, ast_matchers::MatchFinder *parent) + : Replace(Replace), owner(parent) {} - void run(const MatchFinder::MatchResult &Result) override { + void convertKernelDecl(const FunctionDecl * kernelDecl, const MatchFinder::MatchResult &Result) + { + SourceManager * SM = Result.SourceManager; + LangOptions DefaultLangOptions; - SourceManager * SM = Result.SourceManager; + SmallString<40> XStr; + raw_svector_ostream OS(XStr); + StringRef initialParamList; + OS << "hipLaunchParm lp"; + size_t replacementLength = OS.str().size(); + SourceLocation sl = kernelDecl->getNameInfo().getEndLoc(); + SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(sl, clang::tok::l_paren, *SM, DefaultLangOptions, true); + kernelArgListStart.dump(*SM); + if (kernelDecl->getNumParams() > 0) { + const ParmVarDecl * pvdFirst = kernelDecl->getParamDecl(0); + const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams() - 1); + SourceLocation kernelArgListStart(pvdFirst->getLocStart()); + SourceLocation kernelArgListEnd(pvdLast->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); + size_t replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); + initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); + OS << ", " << initialParamList; + } + llvm::outs() << "initial paramlist: " << initialParamList << "\n"; + llvm::outs() << "new paramlist: " << OS.str() << "\n"; + Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); + Replace->insert(Rep0); + } + + void run(const MatchFinder::MatchResult &Result) override { + + SourceManager * SM = Result.SourceManager; + LangOptions DefaultLangOptions; if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) { @@ -406,35 +437,27 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { } } - if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) - { - LangOptions DefaultLangOptions; - StringRef initialParamList; - SmallString<40> XStr; - raw_svector_ostream OS(XStr); - OS << "hipLaunchParm lp"; - const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); - SourceLocation l1 = kernelDecl->getNameInfo().getLocStart(); - l1.dump(*SM);llvm::outs() << "\n"; - SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(l1, clang::tok::l_paren, *SM, DefaultLangOptions, true); - kernelArgListStart.dump(*SM);llvm::outs() << "\n"; - size_t replacementLength = 0; - if (kernelDecl->getNumParams() > 0) { - const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams()-1); - SourceLocation kernelArgListEnd = SourceLocation(pvdLast->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); - replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); - initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); - OS << ", " << initialParamList; + if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) + { + SmallString<40> XStr; + raw_svector_ostream OS(XStr); + StringRef calleeName; + const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); + if (kernelDecl) { + calleeName = kernelDecl->getName(); + convertKernelDecl(kernelDecl, Result); + } + else { + const Expr * e = launchKernel->getCallee(); + if (const UnresolvedLookupExpr * ule = dyn_cast(e)) { + calleeName = ule->getName().getAsIdentifierInfo()->getName(); + owner->addMatcher(functionTemplateDecl(hasName(calleeName)).bind("unresolvedTemplateName"), this); } + } - llvm::outs() << "initial paramlist: " << initialParamList << "\n"; - llvm::outs() << "new paramlist: " << OS.str() << "\n"; - Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); - Replace->insert(Rep0); XStr.clear(); - OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << kernelDecl->getName() << "), "; + OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << calleeName << "), "; const CallExpr * config = launchKernel->getConfig(); llvm::outs() << "\nKernel config arguments:\n"; @@ -475,6 +498,12 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { Replace->insert(Rep); } + if (const FunctionTemplateDecl * templateDecl = Result.Nodes.getNodeAs("unresolvedTemplateName")) + { + FunctionDecl * kernelDecl = templateDecl->getTemplatedDecl(); + convertKernelDecl(kernelDecl, Result); + } + if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) { if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { @@ -591,6 +620,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { private: Replacements *Replace; + ast_matchers::MatchFinder * owner; struct hipName N; }; @@ -631,7 +661,7 @@ int main(int argc, const char **argv) { RefactoringTool Tool(OptionsParser.getCompilations(), dst); ast_matchers::MatchFinder Finder; - Cuda2HipCallback Callback(&Tool.getReplacements()); + Cuda2HipCallback Callback(&Tool.getReplacements(), &Finder); HipifyPPCallbacks PPCallbacks(&Tool.getReplacements()); Finder.addMatcher(callExpr(isExpansionInMainFile(), callee(functionDecl(matchesName("cuda.*")))).bind("cudaCall"), &Callback); Finder.addMatcher(cudaKernelCallExpr().bind("cudaLaunchKernel"), &Callback); @@ -642,8 +672,8 @@ int main(int argc, const char **argv) { Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(pointsTo(cxxRecordDecl(matchesName("cuda.*"))))).bind("cudaStructVarPtr"), &Callback); Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(pointsTo(namedDecl(matchesName("cuda.*"))))).bind("cudaParamDeclPtr"), &Callback); - Finder.addMatcher(expr(sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration(cxxRecordDecl(matchesName("cuda.*"))))))).bind("cudaStructSizeOf"), &Callback); - Finder.addMatcher(stringLiteral().bind("stringLiteral"), &Callback); + Finder.addMatcher(expr(isExpansionInMainFile(), sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration(cxxRecordDecl(matchesName("cuda.*"))))))).bind("cudaStructSizeOf"), &Callback); + Finder.addMatcher(stringLiteral(isExpansionInMainFile()).bind("stringLiteral"), &Callback); auto action = newFrontendActionFactory(&Finder, &PPCallbacks); From d60aa72f6c2ff1e8f0c8cff9d06e8bb4be73fd8e Mon Sep 17 00:00:00 2001 From: dfukalov Date: Sat, 5 Mar 2016 13:59:38 +0300 Subject: [PATCH 26/56] 1. added double dash option to test to avoid warning message about compilation database 2. fixed cmake resource folder discovery for standalone build case --- hipamd/CMakeLists.txt | 1 + hipamd/src/Cuda2Hip.cpp | 3 +++ hipamd/test/axpy.cu | 23 ++++++++++------------- 3 files changed, 14 insertions(+), 13 deletions(-) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 0c209b8fa2..18e8e7df4d 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -53,6 +53,7 @@ if(${HIPIFY_STANDLONE}) set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_CFLAGS}") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS}") set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -std=c++11 -pthread -fno-rtti -fvisibility-inlines-hidden") + set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DHIPIFY_CLANG_RES=\\\"${LLVM_LIBRARY_DIRS}/clang/${LLVM_VERSION_MAJOR}.${LLVM_VERSION_MINOR}.${LLVM_VERSION_PATCH}\\\"") add_subdirectory(test) else() install(TARGETS hipify diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 434d74e584..a9cb162849 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -685,6 +685,9 @@ int main(int argc, const char **argv) { { Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster(Stage, ArgumentInsertPosition::BEGIN)); Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster("-std=c++11")); +#if defined(HIPIFY_CLANG_RES) + Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster("-resource-dir=" HIPIFY_CLANG_RES)); +#endif // defined(HIPIFY_CLANG_HEADERS) Tool.appendArgumentsAdjuster(getClangSyntaxOnlyAdjuster()); Result = Tool.run(action.get()); diff --git a/hipamd/test/axpy.cu b/hipamd/test/axpy.cu index 29d5493763..9e83ccb7e6 100644 --- a/hipamd/test/axpy.cu +++ b/hipamd/test/axpy.cu @@ -1,11 +1,10 @@ -// RUN: hipify "%s" 2>&1 | FileCheck %s - -#include // for checkCudaErrors +// RUN: hipify "%s" -o=%t -- +// RUN: FileCheck %s -input-file=%t --match-full-lines #include __global__ void axpy(float a, float* x, float* y) { - // CHECK: hipThreadIdx_x + // CHECK: y[hipThreadIdx_x] = a * x[hipThreadIdx_x]; y[threadIdx.x] = a * x[threadIdx.x]; } @@ -19,25 +18,23 @@ int main(int argc, char* argv[]) { // Copy input data to device. float* device_x; float* device_y; - checkCudaErrors(cudaMalloc(&device_x, kDataLen * sizeof(float))); - checkCudaErrors(cudaMalloc(&device_y, kDataLen * sizeof(float))); - checkCudaErrors(cudaMemcpy(device_x, host_x, kDataLen * sizeof(float), - cudaMemcpyHostToDevice)); + cudaMalloc(&device_x, kDataLen * sizeof(float)); + cudaMalloc(&device_y, kDataLen * sizeof(float)); + cudaMemcpy(device_x, host_x, kDataLen * sizeof(float), cudaMemcpyHostToDevice); // Launch the kernel. - // CHECK: hipLaunchKernel(HIP_KERNEL_NAME + // CHECK: hipLaunchKernel(HIP_KERNEL_NAME(axpy), dim3(1), dim3(kDataLen), 0, 0, a, device_x, device_y); axpy<<<1, kDataLen>>>(a, device_x, device_y); // Copy output data to host. - checkCudaErrors(cudaDeviceSynchronize()); - checkCudaErrors(cudaMemcpy(host_y, device_y, kDataLen * sizeof(float), - cudaMemcpyDeviceToHost)); + cudaDeviceSynchronize(); + cudaMemcpy(host_y, device_y, kDataLen * sizeof(float), cudaMemcpyDeviceToHost); // Print the results. for (int i = 0; i < kDataLen; ++i) { std::cout << "y[" << i << "] = " << host_y[i] << "\n"; } - checkCudaErrors(cudaDeviceReset()); + cudaDeviceReset(); return 0; } From e6058442e1a6f5e54f3e0c966595cc6005bc185b Mon Sep 17 00:00:00 2001 From: dfukalov Date: Mon, 7 Mar 2016 21:29:23 +0300 Subject: [PATCH 27/56] added -inplace option --- hipamd/src/Cuda2Hip.cpp | 35 ++++++++++++++++++++++++----------- 1 file changed, 24 insertions(+), 11 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index a9cb162849..cfc7c02446 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -629,9 +629,14 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { // Set up the command line options static cl::OptionCategory ToolTemplateCategory("CUDA to HIP source translator options"); static cl::extrahelp MoreHelp( " specify the path of source file\n\n" ); + static cl::opt OutputFilename("o", cl::desc("Output filename"), cl::value_desc("filename"), cl::cat(ToolTemplateCategory)); +static cl::opt +Inplace("inplace", cl::desc("Modify input file inplace, replacing input with hipified output, save backup in .prehip file. " + "If .prehip file exists, use that as input to hip."), cl::value_desc("inplace"), cl::cat(ToolTemplateCategory)); + int main(int argc, const char **argv) { llvm::sys::PrintStackTraceOnErrorSignal(); @@ -643,18 +648,24 @@ int main(int argc, const char **argv) { std::vector fileSources = OptionsParser.getSourcePathList(); if (dst.empty()) { dst = fileSources[0]; - size_t pos = dst.rfind(".cu"); - if (pos != std::string::npos) { - dst = dst.substr(0, pos) + ".hip.cu"; - } else { - llvm::errs() << "Input .cu file was not specified.\n"; - return 1; + if (!Inplace) { + size_t pos = dst.rfind(".cu"); + if (pos != std::string::npos) { + dst = dst.substr(0, pos) + ".hip.cu"; + } else { + llvm::errs() << "Input .cu file was not specified.\n"; + return 1; + } } } else { + if (Inplace) { + llvm::errs() << "Conflict: both -o and -inplace options are specified."; + } dst += ".cu"; } + std::ifstream source(fileSources[0], std::ios::binary); - std::ofstream dest(dst, std::ios::binary); + std::ofstream dest(Inplace ? dst+".prehip" : dst, std::ios::binary); dest << source.rdbuf(); source.close(); dest.close(); @@ -715,10 +726,12 @@ int main(int argc, const char **argv) { Result = Rewrite.overwriteChangedFiles(); - size_t pos = dst.rfind(".cu"); - if (pos != std::string::npos) - { - rename(dst.c_str(), dst.substr(0, pos).c_str()); + if (!Inplace) { + size_t pos = dst.rfind(".cu"); + if (pos != std::string::npos) + { + rename(dst.c_str(), dst.substr(0, pos).c_str()); + } } return Result; } From c6014ab0a430a49e848e53cbff9acabfefbb71f7 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Tue, 8 Mar 2016 02:03:25 +0300 Subject: [PATCH 28/56] moved all debug output into DEBUG() --- hipamd/src/Cuda2Hip.cpp | 73 ++++++++++++++++++++++------------------- 1 file changed, 39 insertions(+), 34 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index cfc7c02446..f895511db8 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -278,9 +278,10 @@ namespace { if (is_angled) { if (N.cuda2hipRename.count(file_name)) { std::string repName = N.cuda2hipRename[file_name]; - llvm::errs() << "\nInclude file found: " << file_name << "\n"; - llvm::errs() << "\nSourceLocation:"; filename_range.getBegin().dump(*_sm); - llvm::errs() << "\nWill be replaced with " << repName << "\n"; + DEBUG(dbgs() << "Include file found: " << file_name << "\n"); + DEBUG(dbgs() << "SourceLocation:" + << filename_range.getBegin().printToString(*_sm) << "\n"); + DEBUG(dbgs() << "Will be replaced with " << repName << "\n"); SourceLocation sl = filename_range.getBegin(); SourceLocation sle = filename_range.getEnd(); const char* B = _sm->getCharacterData(sl); @@ -305,13 +306,12 @@ namespace { StringRef name = T.getIdentifierInfo()->getName(); if (N.cuda2hipRename.count(name)) { StringRef repName = N.cuda2hipRename[name]; - llvm::errs() << "\nIdentifier " << name - << " found in definition of macro " - << MacroNameTok.getIdentifierInfo()->getName() << "\n"; - llvm::errs() << "\nwill be replaced with: " << repName << "\n"; + DEBUG(dbgs() << "Identifier " << name + << " found in definition of macro " + << MacroNameTok.getIdentifierInfo()->getName() << "\n"); + DEBUG(dbgs() << "will be replaced with: " << repName << "\n"); SourceLocation sl = T.getLocation(); - llvm::errs() << "\nSourceLocation: ";sl.dump(*_sm); - llvm::errs() << "\n"; + DEBUG(dbgs() << "SourceLocation: " << sl.printToString(*_sm) << "\n"); Replacement Rep(*_sm, sl, name.size(), repName); Replace->insert(Rep); } @@ -348,10 +348,10 @@ namespace { StringRef name = tok.getIdentifierInfo()->getName(); if (N.cuda2hipRename.count(name)) { StringRef repName = N.cuda2hipRename[name]; - llvm::errs() << "\nIdentifier " << name + DEBUG(dbgs() << "Identifier " << name << " found as an actual argument in expansion of macro " - << macroName << "\n"; - llvm::errs() << "\nwill be replaced with: " << repName << "\n"; + << macroName << "\n"); + DEBUG(dbgs() << "will be replaced with: " << repName << "\n"); SourceLocation sl = tok.getLocation(); Replacement Rep(*_sm, sl, name.size(), repName); Replace->insert(Rep); @@ -402,7 +402,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { size_t replacementLength = OS.str().size(); SourceLocation sl = kernelDecl->getNameInfo().getEndLoc(); SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(sl, clang::tok::l_paren, *SM, DefaultLangOptions, true); - kernelArgListStart.dump(*SM); + DEBUG(dbgs() << kernelArgListStart.printToString(*SM)); if (kernelDecl->getNumParams() > 0) { const ParmVarDecl * pvdFirst = kernelDecl->getParamDecl(0); const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams() - 1); @@ -413,29 +413,29 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); OS << ", " << initialParamList; } - llvm::outs() << "initial paramlist: " << initialParamList << "\n"; - llvm::outs() << "new paramlist: " << OS.str() << "\n"; + DEBUG(dbgs() << "initial paramlist: " << initialParamList << "\n"); + DEBUG(dbgs() << "new paramlist: " << OS.str() << "\n"); Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); Replace->insert(Rep0); - } + } void run(const MatchFinder::MatchResult &Result) override { SourceManager * SM = Result.SourceManager; LangOptions DefaultLangOptions; - if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) - { - const FunctionDecl * funcDcl = call->getDirectCallee(); - std::string name = funcDcl->getDeclName().getAsString(); - if (N.cuda2hipRename.count(name)) { - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = call->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); - Replace->insert(Rep); - } + if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) + { + const FunctionDecl * funcDcl = call->getDirectCallee(); + std::string name = funcDcl->getDeclName().getAsString(); + if (N.cuda2hipRename.count(name)) { + std::string repName = N.cuda2hipRename[name]; + SourceLocation sl = call->getLocStart(); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? + SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + Replace->insert(Rep); } + } if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) { @@ -460,7 +460,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << calleeName << "), "; const CallExpr * config = launchKernel->getConfig(); - llvm::outs() << "\nKernel config arguments:\n"; + DEBUG(dbgs() << "Kernel config arguments:" << "\n"); for (unsigned argno = 0; argno < config->getNumArgs(); argno++) { const Expr * arg = config->getArg(argno); @@ -471,7 +471,8 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { SourceLocation el(arg->getLocEnd()); SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); StringRef outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); - llvm::outs() << "args[ " << argno << "]" << outs << " <" << pvd->getType().getAsString() << ">\n"; + DEBUG(dbgs() << "args[ " << argno << "]" << outs << " <" + << pvd->getType().getAsString() << ">" << "\n"); if (pvd->getType().getAsString().compare("dim3") == 0) OS << " dim3(" << outs << "),"; else @@ -487,7 +488,7 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { SourceLocation el(arg->getLocEnd()); SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); - llvm::outs() << outs.c_str() << "\n"; + DEBUG(dbgs() << outs << "\n"); OS << " " << outs << ","; } XStr.pop_back(); @@ -633,6 +634,10 @@ static cl::extrahelp MoreHelp( " specify the path of source file\n\n" ) static cl::opt OutputFilename("o", cl::desc("Output filename"), cl::value_desc("filename"), cl::cat(ToolTemplateCategory)); +static cl::opt +Debug("debug", cl::desc("Enable debug output"), cl::Hidden, + cl::location(llvm::DebugFlag)); + static cl::opt Inplace("inplace", cl::desc("Modify input file inplace, replacing input with hipified output, save backup in .prehip file. " "If .prehip file exists, use that as input to hip."), cl::value_desc("inplace"), cl::cat(ToolTemplateCategory)); @@ -713,15 +718,15 @@ int main(int argc, const char **argv) { &*DiagOpts, &DiagnosticPrinter, false); SourceManager Sources(Diagnostics, Tool.getFiles()); - llvm::outs() << "Replacements collected by the tool:\n"; - for (auto &r : Tool.getReplacements()) { - llvm::outs() << r.toString() << "\n"; + DEBUG(dbgs() << "Replacements collected by the tool:\n"); + for (const auto &r : Tool.getReplacements()) { + DEBUG(dbgs() << r.toString() << "\n"); } Rewriter Rewrite(Sources, DefaultLangOptions); if (!Tool.applyAllReplacements(Rewrite)) { - llvm::errs() << "Skipped some replacements.\n"; + DEBUG(dbgs() << "Skipped some replacements.\n"); } Result = Rewrite.overwriteChangedFiles(); From f0c01ebd57bc0cabe0272024d1daa925ebc20b9f Mon Sep 17 00:00:00 2001 From: dfukalov Date: Wed, 9 Mar 2016 18:37:20 +0300 Subject: [PATCH 29/56] fixed bug with -debug switch --- hipamd/src/Cuda2Hip.cpp | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index f895511db8..46c60bf5be 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -634,9 +634,8 @@ static cl::extrahelp MoreHelp( " specify the path of source file\n\n" ) static cl::opt OutputFilename("o", cl::desc("Output filename"), cl::value_desc("filename"), cl::cat(ToolTemplateCategory)); -static cl::opt -Debug("debug", cl::desc("Enable debug output"), cl::Hidden, - cl::location(llvm::DebugFlag)); +//static cl::opt +//Debug("debug", cl::desc("Enable debug output"), cl::Hidden, cl::location(llvm::DebugFlag)); static cl::opt Inplace("inplace", cl::desc("Modify input file inplace, replacing input with hipified output, save backup in .prehip file. " From 279d5fedc4d9a9366a23bf0f1d08c43eaaf0973d Mon Sep 17 00:00:00 2001 From: Daniil Fukalov Date: Tue, 22 Mar 2016 14:57:59 +0300 Subject: [PATCH 30/56] added Notes about installing dependent CUDA headers --- hipamd/README.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/hipamd/README.md b/hipamd/README.md index 0ddd4f9b91..e743c48ca0 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -45,3 +45,9 @@ sudo easy_install lit make -C path_to_hipify_src/build test ``` +# Notes +- To run, the tool needs "cuda minimal build" package: + 1. Download target installer from https://developer.nvidia.com/cuda-downloads. Choose "deb(network)" installer type to reduce downloaded packages size (we don't need the whole set) + 2. Run `sudo dpkg -i cuda-repo-ubuntu1404_7.5-18_amd64.deb` + 3. Run `sudo apt-get update` + 4. Run `sudo apt-get install cuda-minimal-build-7-5` - this will install needed files, (without nvidia drivers, runtime, tools etc.) From 84ca2aa72c56b9a8325a7f75af7e3cd9719a0869 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Tue, 22 Mar 2016 17:07:37 +0300 Subject: [PATCH 31/56] 1. renamed hipMallocHost -> hipHostAlloc, hipFreeHost -> hipHostFree 2. added capability to build with llvm/clang 3.8 --- hipamd/src/Cuda2Hip.cpp | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 46c60bf5be..21f3755d69 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -103,9 +103,9 @@ namespace { // Memory management : cuda2hipRename["cudaMalloc"] = "hipMalloc"; - cuda2hipRename["cudaMallocHost"] = "hipMallocHost"; + cuda2hipRename["cudaMallocHost"] = "hipHostAlloc"; cuda2hipRename["cudaFree"] = "hipFree"; - cuda2hipRename["cudaFreeHost"] = "hipFreeHost"; + cuda2hipRename["cudaFreeHost"] = "hipHostFree"; // Coordinate Indexing and Dimensions: cuda2hipRename["threadIdx.x"] = "hipThreadIdx_x"; @@ -334,7 +334,11 @@ namespace { // to workaround the 'const' MacroArgs passed into this hook. const Token * start = Args->getUnexpArgument(i); size_t len = Args->getArgLength(start) + 1; +#if (LLVM_VERSION_MAJOR >= 3) && (LLVM_VERSION_MINOR >= 9) _pp->EnterTokenStream(ArrayRef(start,len), false); +#else + _pp->EnterTokenStream(start, len, false, false); +#endif do { toks.push_back(Token()); Token & tk = toks.back(); From 1ec21c1ac5ee15734f214518863d0713e7b81051 Mon Sep 17 00:00:00 2001 From: Daniil Fukalov Date: Tue, 22 Mar 2016 17:59:11 +0300 Subject: [PATCH 32/56] Update README.md --- hipamd/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/hipamd/README.md b/hipamd/README.md index e743c48ca0..743a1a63b2 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -50,4 +50,4 @@ make -C path_to_hipify_src/build test 1. Download target installer from https://developer.nvidia.com/cuda-downloads. Choose "deb(network)" installer type to reduce downloaded packages size (we don't need the whole set) 2. Run `sudo dpkg -i cuda-repo-ubuntu1404_7.5-18_amd64.deb` 3. Run `sudo apt-get update` - 4. Run `sudo apt-get install cuda-minimal-build-7-5` - this will install needed files, (without nvidia drivers, runtime, tools etc.) + 4. Run `sudo apt-get install cuda-minimal-build-7-5 cuda-curand-dev-7-5` - this will install needed files, (without nvidia drivers, runtime, tools etc.) From 0cdb0dc5ac1923900808aa817bc2b9c99c48be1e Mon Sep 17 00:00:00 2001 From: dfukalov Date: Tue, 22 Mar 2016 19:48:29 +0300 Subject: [PATCH 33/56] migrating from std::string to StringRef --- hipamd/src/Cuda2Hip.cpp | 48 ++++++++++++++++++++--------------------- 1 file changed, 24 insertions(+), 24 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index 21f3755d69..d80e685c23 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -277,7 +277,7 @@ namespace { if (_sm->isWrittenInMainFile(hash_loc)) { if (is_angled) { if (N.cuda2hipRename.count(file_name)) { - std::string repName = N.cuda2hipRename[file_name]; + StringRef repName = N.cuda2hipRename[file_name]; DEBUG(dbgs() << "Include file found: " << file_name << "\n"); DEBUG(dbgs() << "SourceLocation:" << filename_range.getBegin().printToString(*_sm) << "\n"); @@ -286,8 +286,8 @@ namespace { SourceLocation sle = filename_range.getEnd(); const char* B = _sm->getCharacterData(sl); const char* E = _sm->getCharacterData(sle); - repName = "<" + repName + ">"; - Replacement Rep(*_sm, sl, E - B, repName); + SmallString<128> tmpData; + Replacement Rep(*_sm, sl, E - B, Twine("<" + repName + ">").toStringRef(tmpData)); Replace->insert(Rep); } } @@ -431,12 +431,12 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) { const FunctionDecl * funcDcl = call->getDirectCallee(); - std::string name = funcDcl->getDeclName().getAsString(); + StringRef name = funcDcl->getDeclName().getAsString(); if (N.cuda2hipRename.count(name)) { - std::string repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name]; SourceLocation sl = call->getLocStart(); Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.length(), repName); + SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); Replace->insert(Rep); } } @@ -513,14 +513,15 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { { if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { - std::string name = declRef->getDecl()->getNameAsString(); - std::string memberName = threadIdx->getMemberDecl()->getNameAsString(); - size_t pos = memberName.find_first_not_of("__fetch_builtin_"); - memberName = memberName.substr(pos, memberName.length() - pos); - name += "." + memberName; - std::string repName = N.cuda2hipRename[name]; - SourceLocation sl = threadIdx->getLocStart(); - Replacement Rep(*SM, sl, name.length(), repName); + StringRef name = declRef->getDecl()->getName(); + StringRef memberName = threadIdx->getMemberDecl()->getName(); + size_t pos = memberName.find_first_not_of("__fetch_builtin_"); + memberName = memberName.slice(pos, memberName.size()); + SmallString<128> tmpData; + name = Twine(name+"."+memberName).toStringRef(tmpData); + StringRef repName = N.cuda2hipRename[name]; + SourceLocation sl = threadIdx->getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } } @@ -528,30 +529,29 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { if (const DeclRefExpr * cudaEnumConstantRef = Result.Nodes.getNodeAs("cudaEnumConstantRef")) { - std::string name = cudaEnumConstantRef->getDecl()->getNameAsString(); - std::string repName = N.cuda2hipRename[name]; + StringRef name = cudaEnumConstantRef->getDecl()->getNameAsString(); + StringRef repName = N.cuda2hipRename[name]; SourceLocation sl = cudaEnumConstantRef->getLocStart(); - Replacement Rep(*SM, sl, name.length(), repName); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } if (const VarDecl * cudaEnumConstantDecl = Result.Nodes.getNodeAs("cudaEnumConstantDecl")) { - std::string name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); - std::string repName = N.cuda2hipRename[name]; + StringRef name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); + StringRef repName = N.cuda2hipRename[name]; SourceLocation sl = cudaEnumConstantDecl->getLocStart(); - Replacement Rep(*SM, sl, name.length(), repName); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } if (const VarDecl * cudaStructVar = Result.Nodes.getNodeAs("cudaStructVar")) { - std::string name = - cudaStructVar->getType()->getAsStructureType()->getDecl()->getNameAsString(); - std::string repName = N.cuda2hipRename[name]; + StringRef name = cudaStructVar->getType()->getAsStructureType()->getDecl()->getNameAsString(); + StringRef repName = N.cuda2hipRename[name]; TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.length(), repName); + Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } From 403f5c71bd7ec1ff908ea53f8bc3ed977aa3eb53 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Thu, 24 Mar 2016 14:54:14 +0300 Subject: [PATCH 34/56] source reformatted to LLVM style, minor cleanups --- hipamd/src/Cuda2Hip.cpp | 905 +++++++++++++++++++++------------------- 1 file changed, 479 insertions(+), 426 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index d80e685c23..db8527835f 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -24,28 +24,28 @@ THE SOFTWARE. * * This file is compiled and linked into clang based hipify tool. */ -#include "clang/ASTMatchers/ASTMatchers.h" #include "clang/ASTMatchers/ASTMatchFinder.h" +#include "clang/ASTMatchers/ASTMatchers.h" #include "clang/Basic/SourceManager.h" +#include "clang/Frontend/CompilerInstance.h" #include "clang/Frontend/FrontendActions.h" +#include "clang/Frontend/TextDiagnosticPrinter.h" #include "clang/Lex/Lexer.h" +#include "clang/Lex/MacroArgs.h" +#include "clang/Lex/MacroInfo.h" +#include "clang/Lex/PPCallbacks.h" +#include "clang/Lex/Preprocessor.h" +#include "clang/Rewrite/Core/Rewriter.h" #include "clang/Tooling/CommonOptionsParser.h" #include "clang/Tooling/Refactoring.h" #include "clang/Tooling/Tooling.h" #include "llvm/Support/CommandLine.h" +#include "llvm/Support/Debug.h" #include "llvm/Support/MemoryBuffer.h" #include "llvm/Support/Signals.h" -#include "llvm/Support/Debug.h" -#include "clang/Frontend/TextDiagnosticPrinter.h" -#include "clang/Rewrite/Core/Rewriter.h" -#include "clang/Lex/MacroInfo.h" -#include "clang/Frontend/CompilerInstance.h" -#include "clang/Lex/Preprocessor.h" -#include "clang/Lex/PPCallbacks.h" -#include "clang/Lex/MacroArgs.h" -#include #include +#include using namespace clang; using namespace clang::ast_matchers; @@ -55,428 +55,436 @@ using namespace llvm; #define DEBUG_TYPE "cuda2hip" namespace { - struct hipName { +struct hipName { hipName() { - // defines - cuda2hipRename["__CUDACC__"] = "__HIPCC__"; + // defines + cuda2hipRename["__CUDACC__"] = "__HIPCC__"; - // includes - cuda2hipRename["cuda_runtime.h"] = "hip_runtime.h"; - cuda2hipRename["cuda_runtime_api.h"] = "hip_runtime_api.h"; + // includes + cuda2hipRename["cuda_runtime.h"] = "hip_runtime.h"; + cuda2hipRename["cuda_runtime_api.h"] = "hip_runtime_api.h"; - // Error codes and return types: - cuda2hipRename["cudaError_t"] = "hipError_t"; - cuda2hipRename["cudaError"] = "hipError"; - cuda2hipRename["cudaSuccess"] = "hipSuccess"; + // Error codes and return types: + cuda2hipRename["cudaError_t"] = "hipError_t"; + cuda2hipRename["cudaError"] = "hipError"; + cuda2hipRename["cudaSuccess"] = "hipSuccess"; - cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; - cuda2hipRename["cudaErrorMemoryAllocation"] = "hipErrorMemoryAllocation"; - cuda2hipRename["cudaErrorMemoryFree"] = "hipErrorMemoryFree"; - cuda2hipRename["cudaErrorUnknownSymbol"] = "hipErrorUnknownSymbol"; - cuda2hipRename["cudaErrorOutOfResources"] = "hipErrorOutOfResources"; - cuda2hipRename["cudaErrorInvalidValue"] = "hipErrorInvalidValue"; - cuda2hipRename["cudaErrorInvalidResourceHandle"] = "hipErrorInvalidResourceHandle"; - cuda2hipRename["cudaErrorInvalidDevice"] = "hipErrorInvalidDevice"; - cuda2hipRename["cudaErrorNoDevice"] = "hipErrorNoDevice"; - cuda2hipRename["cudaErrorNotReady"] = "hipErrorNotReady"; - cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; + cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; + cuda2hipRename["cudaErrorMemoryAllocation"] = "hipErrorMemoryAllocation"; + cuda2hipRename["cudaErrorMemoryFree"] = "hipErrorMemoryFree"; + cuda2hipRename["cudaErrorUnknownSymbol"] = "hipErrorUnknownSymbol"; + cuda2hipRename["cudaErrorOutOfResources"] = "hipErrorOutOfResources"; + cuda2hipRename["cudaErrorInvalidValue"] = "hipErrorInvalidValue"; + cuda2hipRename["cudaErrorInvalidResourceHandle"] = + "hipErrorInvalidResourceHandle"; + cuda2hipRename["cudaErrorInvalidDevice"] = "hipErrorInvalidDevice"; + cuda2hipRename["cudaErrorNoDevice"] = "hipErrorNoDevice"; + cuda2hipRename["cudaErrorNotReady"] = "hipErrorNotReady"; + cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; - // error APIs: - cuda2hipRename["cudaGetLastError"] = "hipGetLastError"; - cuda2hipRename["cudaPeekAtLastError"] = "hipPeekAtLastError"; - cuda2hipRename["cudaGetErrorName"] = "hipGetErrorName"; - cuda2hipRename["cudaGetErrorString"] = "hipGetErrorString"; + // error APIs: + cuda2hipRename["cudaGetLastError"] = "hipGetLastError"; + cuda2hipRename["cudaPeekAtLastError"] = "hipPeekAtLastError"; + cuda2hipRename["cudaGetErrorName"] = "hipGetErrorName"; + cuda2hipRename["cudaGetErrorString"] = "hipGetErrorString"; - // Memcpy - cuda2hipRename["cudaMemcpy"] = "hipMemcpy"; - cuda2hipRename["cudaMemcpyHostToHost"] = "hipMemcpyHostToHost"; - cuda2hipRename["cudaMemcpyHostToDevice"] = "hipMemcpyHostToDevice"; - cuda2hipRename["cudaMemcpyDeviceToHost"] = "hipMemcpyDeviceToHost"; - cuda2hipRename["cudaMemcpyDeviceToDevice"] = "hipMemcpyDeviceToDevice"; - cuda2hipRename["cudaMemcpyDefault"] = "hipMemcpyDefault"; - cuda2hipRename["cudaMemcpyToSymbol"] = "hipMemcpyToSymbol"; - cuda2hipRename["cudaMemset"] = "hipMemset"; - cuda2hipRename["cudaMemsetAsync"] = "hipMemsetAsync"; - cuda2hipRename["cudaMemcpyAsync"] = "hipMemcpyAsync"; - cuda2hipRename["cudaMemGetInfo"] = "hipMemGetInfo"; - cuda2hipRename["cudaMemcpyKind"] = "hipMemcpyKind"; + // Memcpy + cuda2hipRename["cudaMemcpy"] = "hipMemcpy"; + cuda2hipRename["cudaMemcpyHostToHost"] = "hipMemcpyHostToHost"; + cuda2hipRename["cudaMemcpyHostToDevice"] = "hipMemcpyHostToDevice"; + cuda2hipRename["cudaMemcpyDeviceToHost"] = "hipMemcpyDeviceToHost"; + cuda2hipRename["cudaMemcpyDeviceToDevice"] = "hipMemcpyDeviceToDevice"; + cuda2hipRename["cudaMemcpyDefault"] = "hipMemcpyDefault"; + cuda2hipRename["cudaMemcpyToSymbol"] = "hipMemcpyToSymbol"; + cuda2hipRename["cudaMemset"] = "hipMemset"; + cuda2hipRename["cudaMemsetAsync"] = "hipMemsetAsync"; + cuda2hipRename["cudaMemcpyAsync"] = "hipMemcpyAsync"; + cuda2hipRename["cudaMemGetInfo"] = "hipMemGetInfo"; + cuda2hipRename["cudaMemcpyKind"] = "hipMemcpyKind"; - // Memory management : - cuda2hipRename["cudaMalloc"] = "hipMalloc"; - cuda2hipRename["cudaMallocHost"] = "hipHostAlloc"; - cuda2hipRename["cudaFree"] = "hipFree"; - cuda2hipRename["cudaFreeHost"] = "hipHostFree"; + // Memory management : + cuda2hipRename["cudaMalloc"] = "hipMalloc"; + cuda2hipRename["cudaMallocHost"] = "hipHostAlloc"; + cuda2hipRename["cudaFree"] = "hipFree"; + cuda2hipRename["cudaFreeHost"] = "hipHostFree"; - // Coordinate Indexing and Dimensions: - cuda2hipRename["threadIdx.x"] = "hipThreadIdx_x"; - cuda2hipRename["threadIdx.y"] = "hipThreadIdx_y"; - cuda2hipRename["threadIdx.z"] = "hipThreadIdx_z"; + // Coordinate Indexing and Dimensions: + cuda2hipRename["threadIdx.x"] = "hipThreadIdx_x"; + cuda2hipRename["threadIdx.y"] = "hipThreadIdx_y"; + cuda2hipRename["threadIdx.z"] = "hipThreadIdx_z"; - cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; - cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; - cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; + cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; + cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; + cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; - cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; - cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; - cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; + cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; + cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; + cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; - cuda2hipRename["gridDim.x"] = "hipGridDim_x"; - cuda2hipRename["gridDim.y"] = "hipGridDim_y"; - cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + cuda2hipRename["gridDim.x"] = "hipGridDim_x"; + cuda2hipRename["gridDim.y"] = "hipGridDim_y"; + cuda2hipRename["gridDim.z"] = "hipGridDim_z"; - cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; - cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; - cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; + cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; + cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; + cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; - cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; - cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; - cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; + cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; + cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; + cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; - cuda2hipRename["gridDim.x"] = "hipGridDim_x"; - cuda2hipRename["gridDim.y"] = "hipGridDim_y"; - cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + cuda2hipRename["gridDim.x"] = "hipGridDim_x"; + cuda2hipRename["gridDim.y"] = "hipGridDim_y"; + cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + cuda2hipRename["warpSize"] = "hipWarpSize"; - cuda2hipRename["warpSize"] = "hipWarpSize"; + // Events + cuda2hipRename["cudaEvent_t"] = "hipEvent_t"; + cuda2hipRename["cudaEventCreate"] = "hipEventCreate"; + cuda2hipRename["cudaEventCreateWithFlags"] = "hipEventCreateWithFlags"; + cuda2hipRename["cudaEventDestroy"] = "hipEventDestroy"; + cuda2hipRename["cudaEventRecord"] = "hipEventRecord"; + cuda2hipRename["cudaEventElapsedTime"] = "hipEventElapsedTime"; + cuda2hipRename["cudaEventSynchronize"] = "hipEventSynchronize"; - // Events - cuda2hipRename["cudaEvent_t"] = "hipEvent_t"; - cuda2hipRename["cudaEventCreate"] = "hipEventCreate"; - cuda2hipRename["cudaEventCreateWithFlags"] = "hipEventCreateWithFlags"; - cuda2hipRename["cudaEventDestroy"] = "hipEventDestroy"; - cuda2hipRename["cudaEventRecord"] = "hipEventRecord"; - cuda2hipRename["cudaEventElapsedTime"] = "hipEventElapsedTime"; - cuda2hipRename["cudaEventSynchronize"] = "hipEventSynchronize"; + // Streams + cuda2hipRename["cudaStream_t"] = "hipStream_t"; + cuda2hipRename["cudaStreamCreate"] = "hipStreamCreate"; + cuda2hipRename["cudaStreamCreateWithFlags"] = "hipStreamCreateWithFlags"; + cuda2hipRename["cudaStreamDestroy"] = "hipStreamDestroy"; + cuda2hipRename["cudaStreamWaitEvent"] = "hipStreamWaitEven"; + cuda2hipRename["cudaStreamSynchronize"] = "hipStreamSynchronize"; + cuda2hipRename["cudaStreamDefault"] = "hipStreamDefault"; + cuda2hipRename["cudaStreamNonBlocking"] = "hipStreamNonBlocking"; - // Streams - cuda2hipRename["cudaStream_t"] = "hipStream_t"; - cuda2hipRename["cudaStreamCreate"] = "hipStreamCreate"; - cuda2hipRename["cudaStreamCreateWithFlags"] = "hipStreamCreateWithFlags"; - cuda2hipRename["cudaStreamDestroy"] = "hipStreamDestroy"; - cuda2hipRename["cudaStreamWaitEvent"] = "hipStreamWaitEven"; - cuda2hipRename["cudaStreamSynchronize"] = "hipStreamSynchronize"; - cuda2hipRename["cudaStreamDefault"] = "hipStreamDefault"; - cuda2hipRename["cudaStreamNonBlocking"] = "hipStreamNonBlocking"; + // Other synchronization + cuda2hipRename["cudaDeviceSynchronize"] = "hipDeviceSynchronize"; + cuda2hipRename["cudaThreadSynchronize"] = + "hipDeviceSynchronize"; // translate deprecated cudaThreadSynchronize + cuda2hipRename["cudaDeviceReset"] = "hipDeviceReset"; + cuda2hipRename["cudaThreadExit"] = + "hipDeviceReset"; // translate deprecated cudaThreadExit + cuda2hipRename["cudaSetDevice"] = "hipSetDevice"; + cuda2hipRename["cudaGetDevice"] = "hipGetDevice"; - // Other synchronization - cuda2hipRename["cudaDeviceSynchronize"] = "hipDeviceSynchronize"; - cuda2hipRename["cudaThreadSynchronize"] = "hipDeviceSynchronize"; // translate deprecated cudaThreadSynchronize - cuda2hipRename["cudaDeviceReset"] = "hipDeviceReset"; - cuda2hipRename["cudaThreadExit"] = "hipDeviceReset"; // translate deprecated cudaThreadExit - cuda2hipRename["cudaSetDevice"] = "hipSetDevice"; - cuda2hipRename["cudaGetDevice"] = "hipGetDevice"; + // Device + cuda2hipRename["cudaDeviceProp"] = "hipDeviceProp_t"; + cuda2hipRename["cudaGetDeviceProperties"] = "hipDeviceGetProperties"; - // Device - cuda2hipRename["cudaDeviceProp"] = "hipDeviceProp_t"; - cuda2hipRename["cudaGetDeviceProperties"] = "hipDeviceGetProperties"; + // Cache config + cuda2hipRename["cudaDeviceSetCacheConfig"] = "hipDeviceSetCacheConfig"; + cuda2hipRename["cudaThreadSetCacheConfig"] = + "hipDeviceSetCacheConfig"; // translate deprecated + cuda2hipRename["cudaDeviceGetCacheConfig"] = "hipDeviceGetCacheConfig"; + cuda2hipRename["cudaThreadGetCacheConfig"] = + "hipDeviceGetCacheConfig"; // translate deprecated + cuda2hipRename["cudaFuncCache"] = "hipFuncCache"; + cuda2hipRename["cudaFuncCachePreferNone"] = "hipFuncCachePreferNone"; + cuda2hipRename["cudaFuncCachePreferShared"] = "hipFuncCachePreferShared"; + cuda2hipRename["cudaFuncCachePreferL1"] = "hipFuncCachePreferL1"; + cuda2hipRename["cudaFuncCachePreferEqual"] = "hipFuncCachePreferEqual"; + // function + cuda2hipRename["cudaFuncSetCacheConfig"] = "hipFuncSetCacheConfig"; - // Cache config - cuda2hipRename["cudaDeviceSetCacheConfig"] = "hipDeviceSetCacheConfig"; - cuda2hipRename["cudaThreadSetCacheConfig"] = "hipDeviceSetCacheConfig"; // translate deprecated - cuda2hipRename["cudaDeviceGetCacheConfig"] = "hipDeviceGetCacheConfig"; - cuda2hipRename["cudaThreadGetCacheConfig"] = "hipDeviceGetCacheConfig"; // translate deprecated - cuda2hipRename["cudaFuncCache"] = "hipFuncCache"; - cuda2hipRename["cudaFuncCachePreferNone"] = "hipFuncCachePreferNone"; - cuda2hipRename["cudaFuncCachePreferShared"] = "hipFuncCachePreferShared"; - cuda2hipRename["cudaFuncCachePreferL1"] = "hipFuncCachePreferL1"; - cuda2hipRename["cudaFuncCachePreferEqual"] = "hipFuncCachePreferEqual"; - // function - cuda2hipRename["cudaFuncSetCacheConfig"] = "hipFuncSetCacheConfig"; + cuda2hipRename["cudaDriverGetVersion"] = "hipDriverGetVersion"; + cuda2hipRename["cudaRuntimeGetVersion"] = "hipRuntimeGetVersion"; - cuda2hipRename["cudaDriverGetVersion"] = "hipDriverGetVersion"; - cuda2hipRename["cudaRuntimeGetVersion"] = "hipRuntimeGetVersion"; + // Peer2Peer + cuda2hipRename["cudaDeviceCanAccessPeer"] = "hipDeviceCanAccessPeer"; + cuda2hipRename["cudaDeviceDisablePeerAccess"] = + "hipDeviceDisablePeerAccess"; + cuda2hipRename["cudaDeviceEnablePeerAccess"] = "hipDeviceEnablePeerAccess"; + cuda2hipRename["cudaMemcpyPeerAsync"] = "hipMemcpyPeerAsync"; + cuda2hipRename["cudaMemcpyPeer"] = "hipMemcpyPeer"; - // Peer2Peer - cuda2hipRename["cudaDeviceCanAccessPeer"] = "hipDeviceCanAccessPeer"; - cuda2hipRename["cudaDeviceDisablePeerAccess"] = "hipDeviceDisablePeerAccess"; - cuda2hipRename["cudaDeviceEnablePeerAccess"] = "hipDeviceEnablePeerAccess"; - cuda2hipRename["cudaMemcpyPeerAsync"] = "hipMemcpyPeerAsync"; - cuda2hipRename["cudaMemcpyPeer"] = "hipMemcpyPeer"; + // Shared mem: + cuda2hipRename["cudaDeviceSetSharedMemConfig"] = + "hipDeviceSetSharedMemConfig"; + cuda2hipRename["cudaThreadSetSharedMemConfig"] = + "hipDeviceSetSharedMemConfig"; // translate deprecated + cuda2hipRename["cudaDeviceGetSharedMemConfig"] = + "hipDeviceGetSharedMemConfig"; + cuda2hipRename["cudaThreadGetSharedMemConfig"] = + "hipDeviceGetSharedMemConfig"; // translate deprecated + cuda2hipRename["cudaSharedMemConfig"] = "hipSharedMemConfig"; + cuda2hipRename["cudaSharedMemBankSizeDefault"] = + "hipSharedMemBankSizeDefault"; + cuda2hipRename["cudaSharedMemBankSizeFourByte"] = + "hipSharedMemBankSizeFourByte"; + cuda2hipRename["cudaSharedMemBankSizeEightByte"] = + "hipSharedMemBankSizeEightByte"; - // Shared mem: - cuda2hipRename["cudaDeviceSetSharedMemConfig"] = "hipDeviceSetSharedMemConfig"; - cuda2hipRename["cudaThreadSetSharedMemConfig"] = "hipDeviceSetSharedMemConfig"; // translate deprecated - cuda2hipRename["cudaDeviceGetSharedMemConfig"] = "hipDeviceGetSharedMemConfig"; - cuda2hipRename["cudaThreadGetSharedMemConfig"] = "hipDeviceGetSharedMemConfig"; // translate deprecated - cuda2hipRename["cudaSharedMemConfig"] = "hipSharedMemConfig"; - cuda2hipRename["cudaSharedMemBankSizeDefault"] = "hipSharedMemBankSizeDefault"; - cuda2hipRename["cudaSharedMemBankSizeFourByte"] = "hipSharedMemBankSizeFourByte"; - cuda2hipRename["cudaSharedMemBankSizeEightByte"] = "hipSharedMemBankSizeEightByte"; + cuda2hipRename["cudaGetDeviceCount"] = "hipGetDeviceCount"; - cuda2hipRename["cudaGetDeviceCount"] = "hipGetDeviceCount"; + // Profiler + // cuda2hipRename["cudaProfilerInitialize"] = "hipProfilerInitialize"; // + // see if these are called anywhere. + cuda2hipRename["cudaProfilerStart"] = "hipProfilerStart"; + cuda2hipRename["cudaProfilerStop"] = "hipProfilerStop"; - // Profiler - //cuda2hipRename["cudaProfilerInitialize"] = "hipProfilerInitialize"; // see if these are called anywhere. - cuda2hipRename["cudaProfilerStart"] = "hipProfilerStart"; - cuda2hipRename["cudaProfilerStop"] = "hipProfilerStop"; + cuda2hipRename["cudaChannelFormatDesc"] = "hipChannelFormatDesc"; + cuda2hipRename["cudaFilterModePoint"] = "hipFilterModePoint"; + cuda2hipRename["cudaReadModeElementType"] = "hipReadModeElementType"; - cuda2hipRename["cudaChannelFormatDesc"] = "hipChannelFormatDesc"; - cuda2hipRename["cudaFilterModePoint"] = "hipFilterModePoint"; - cuda2hipRename["cudaReadModeElementType"] = "hipReadModeElementType"; + cuda2hipRename["cudaCreateChannelDesc"] = "hipCreateChannelDesc"; + cuda2hipRename["cudaBindTexture"] = "hipBindTexture"; + cuda2hipRename["cudaUnbindTexture"] = "hipUnbindTexture"; + } + DenseMap cuda2hipRename; +}; - cuda2hipRename["cudaCreateChannelDesc"] = "hipCreateChannelDesc"; - cuda2hipRename["cudaBindTexture"] = "hipBindTexture"; - cuda2hipRename["cudaUnbindTexture"] = "hipUnbindTexture"; +StringRef unquoteStr(StringRef s) { + if (s.size() > 1 && s.front() == '"' && s.back() == '"') + return s.substr(1, s.size() - 2); + return s; +} + +void processString(StringRef s, struct hipName &map, Replacements *Replace, + SourceManager &SM, SourceLocation start) { + size_t begin = 0; + while ((begin = s.find("cuda", begin)) != StringRef::npos) { + const size_t end = s.find_first_of(" ", begin + 4); + StringRef name = s.slice(begin, end); + StringRef repName = map.cuda2hipRename[name]; + if (!repName.empty()) { + SourceLocation sl = start.getLocWithOffset(begin + 1); + Replacement Rep(SM, sl, name.size(), repName); + Replace->insert(Rep); } - DenseMap cuda2hipRename; - }; + if (end == StringRef::npos) + break; + begin = end + 1; + } +} - StringRef unquoteStr(StringRef s) { - if (s.size() > 1 && s.front() == '"' && s.back() == '"') - return s.substr(1, s.size()-2); - return s; +struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { + HipifyPPCallbacks(Replacements *R) + : SeenEnd(false), _sm(nullptr), _pp(nullptr), Replace(R) {} + + virtual bool handleBeginSource(CompilerInstance &CI, + StringRef Filename) override { + Preprocessor &PP = CI.getPreprocessor(); + SourceManager &SM = CI.getSourceManager(); + setSourceManager(&SM); + PP.addPPCallbacks(std::unique_ptr(this)); + PP.Retain(); + setPreprocessor(&PP); + return true; } - void processString(StringRef s, struct hipName & map, - Replacements * Replace, SourceManager & SM, SourceLocation start) - { - size_t begin = 0; - while ((begin = s.find("cuda", begin)) != StringRef::npos) { - const size_t end = s.find_first_of(" ", begin + 4); - StringRef name = s.slice(begin, end); - StringRef repName = map.cuda2hipRename[name]; - if (!repName.empty()) { - SourceLocation sl = start.getLocWithOffset(begin + 1); - Replacement Rep(SM, sl, name.size(), repName); - Replace->insert(Rep); + virtual void InclusionDirective(SourceLocation hash_loc, + const Token &include_token, + StringRef file_name, bool is_angled, + CharSourceRange filename_range, + const FileEntry *file, StringRef search_path, + StringRef relative_path, + const clang::Module *imported) override { + if (_sm->isWrittenInMainFile(hash_loc)) { + if (is_angled) { + if (N.cuda2hipRename.count(file_name)) { + StringRef repName = N.cuda2hipRename[file_name]; + DEBUG(dbgs() << "Include file found: " << file_name << "\n" + << "SourceLocation:" + << filename_range.getBegin().printToString(*_sm) << "\n" + << "Will be replaced with " << repName << "\n"); + SourceLocation sl = filename_range.getBegin(); + SourceLocation sle = filename_range.getEnd(); + const char *B = _sm->getCharacterData(sl); + const char *E = _sm->getCharacterData(sle); + SmallString<128> tmpData; + Replacement Rep(*_sm, sl, E - B, + Twine("<" + repName + ">").toStringRef(tmpData)); + Replace->insert(Rep); + } } - if (end == StringRef::npos) break; - begin = end + 1; } } - - struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { - HipifyPPCallbacks(Replacements * R) - : SeenEnd(false), _sm(nullptr), _pp(nullptr), Replace(R) - { - } - - virtual bool handleBeginSource(CompilerInstance &CI, StringRef Filename) override - { - Preprocessor &PP = CI.getPreprocessor(); - SourceManager & SM = CI.getSourceManager(); - setSourceManager(&SM); - PP.addPPCallbacks(std::unique_ptr(this)); - PP.Retain(); - setPreprocessor(&PP); - return true; - } - - virtual void InclusionDirective( - SourceLocation hash_loc, - const Token &include_token, - StringRef file_name, - bool is_angled, - CharSourceRange filename_range, - const FileEntry *file, - StringRef search_path, - StringRef relative_path, - const clang::Module *imported) override - { - if (_sm->isWrittenInMainFile(hash_loc)) { - if (is_angled) { - if (N.cuda2hipRename.count(file_name)) { - StringRef repName = N.cuda2hipRename[file_name]; - DEBUG(dbgs() << "Include file found: " << file_name << "\n"); - DEBUG(dbgs() << "SourceLocation:" - << filename_range.getBegin().printToString(*_sm) << "\n"); - DEBUG(dbgs() << "Will be replaced with " << repName << "\n"); - SourceLocation sl = filename_range.getBegin(); - SourceLocation sle = filename_range.getEnd(); - const char* B = _sm->getCharacterData(sl); - const char* E = _sm->getCharacterData(sle); - SmallString<128> tmpData; - Replacement Rep(*_sm, sl, E - B, Twine("<" + repName + ">").toStringRef(tmpData)); + virtual void MacroDefined(const Token &MacroNameTok, + const MacroDirective *MD) override { + if (_sm->isWrittenInMainFile(MD->getLocation()) && + MD->getKind() == MacroDirective::MD_Define) { + for (auto T : MD->getMacroInfo()->tokens()) { + if (T.isAnyIdentifier()) { + StringRef name = T.getIdentifierInfo()->getName(); + if (N.cuda2hipRename.count(name)) { + StringRef repName = N.cuda2hipRename[name]; + SourceLocation sl = T.getLocation(); + DEBUG(dbgs() << "Identifier " << name + << " found in definition of macro " + << MacroNameTok.getIdentifierInfo()->getName() << "\n" + << "will be replaced with: " << repName << "\n" + << "SourceLocation: " << sl.printToString(*_sm) + << "\n"); + Replacement Rep(*_sm, sl, name.size(), repName); Replace->insert(Rep); } } } } + } - virtual void MacroDefined(const Token &MacroNameTok, - const MacroDirective *MD) override - { - if (_sm->isWrittenInMainFile(MD->getLocation()) && - MD->getKind() == MacroDirective::MD_Define) - { - for (auto T : MD->getMacroInfo()->tokens()) - { - if (T.isAnyIdentifier()) { - StringRef name = T.getIdentifierInfo()->getName(); + virtual void MacroExpands(const Token &MacroNameTok, + const MacroDefinition &MD, SourceRange Range, + const MacroArgs *Args) override { + if (_sm->isWrittenInMainFile(MacroNameTok.getLocation())) { + for (unsigned int i = 0; Args && i < MD.getMacroInfo()->getNumArgs(); + i++) { + StringRef macroName = MacroNameTok.getIdentifierInfo()->getName(); + std::vector toks; + // Code below is a kind of stolen from 'MacroArgs::getPreExpArgument' + // to workaround the 'const' MacroArgs passed into this hook. + const Token *start = Args->getUnexpArgument(i); + size_t len = Args->getArgLength(start) + 1; +#if (LLVM_VERSION_MAJOR >= 3) && (LLVM_VERSION_MINOR >= 9) + _pp->EnterTokenStream(ArrayRef(start, len), false); +#else + _pp->EnterTokenStream(start, len, false, false); +#endif + do { + toks.push_back(Token()); + Token &tk = toks.back(); + _pp->Lex(tk); + } while (toks.back().isNot(tok::eof)); + _pp->RemoveTopOfLexerStack(); + // end of stolen code + for (auto tok : toks) { + if (tok.isAnyIdentifier()) { + StringRef name = tok.getIdentifierInfo()->getName(); if (N.cuda2hipRename.count(name)) { StringRef repName = N.cuda2hipRename[name]; DEBUG(dbgs() << "Identifier " << name - << " found in definition of macro " - << MacroNameTok.getIdentifierInfo()->getName() << "\n"); - DEBUG(dbgs() << "will be replaced with: " << repName << "\n"); - SourceLocation sl = T.getLocation(); - DEBUG(dbgs() << "SourceLocation: " << sl.printToString(*_sm) << "\n"); + << " found as an actual argument in expansion of macro " + << macroName << "\n" + << "will be replaced with: " << repName << "\n"); + SourceLocation sl = tok.getLocation(); Replacement Rep(*_sm, sl, name.size(), repName); Replace->insert(Rep); } } - } - } - } - - virtual void MacroExpands(const Token &MacroNameTok, - const MacroDefinition &MD, SourceRange Range, - const MacroArgs *Args) override - { - if (_sm->isWrittenInMainFile(MacroNameTok.getLocation())) - { - for (unsigned int i = 0; Args && i < MD.getMacroInfo()->getNumArgs(); i++) - { - StringRef macroName = MacroNameTok.getIdentifierInfo()->getName(); - std::vector toks; - // Code below is a kind of stolen from 'MacroArgs::getPreExpArgument' - // to workaround the 'const' MacroArgs passed into this hook. - const Token * start = Args->getUnexpArgument(i); - size_t len = Args->getArgLength(start) + 1; -#if (LLVM_VERSION_MAJOR >= 3) && (LLVM_VERSION_MINOR >= 9) - _pp->EnterTokenStream(ArrayRef(start,len), false); -#else - _pp->EnterTokenStream(start, len, false, false); -#endif - do { - toks.push_back(Token()); - Token & tk = toks.back(); - _pp->Lex(tk); - } while (toks.back().isNot(tok::eof)); - _pp->RemoveTopOfLexerStack(); - // end of stolen code - for (auto tok : toks) { - if (tok.isAnyIdentifier()) - { - StringRef name = tok.getIdentifierInfo()->getName(); - if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name]; - DEBUG(dbgs() << "Identifier " << name - << " found as an actual argument in expansion of macro " - << macroName << "\n"); - DEBUG(dbgs() << "will be replaced with: " << repName << "\n"); - SourceLocation sl = tok.getLocation(); - Replacement Rep(*_sm, sl, name.size(), repName); - Replace->insert(Rep); - } - } - if (tok.is(tok::string_literal)) - { - StringRef s(tok.getLiteralData(), tok.getLength()); - processString(unquoteStr(s), N, Replace, *_sm, tok.getLocation()); - } + if (tok.is(tok::string_literal)) { + StringRef s(tok.getLiteralData(), tok.getLength()); + processString(unquoteStr(s), N, Replace, *_sm, tok.getLocation()); } } } } + } - void EndOfMainFile() override - { + void EndOfMainFile() override {} - } + bool SeenEnd; + void setSourceManager(SourceManager *sm) { _sm = sm; } + void setPreprocessor(Preprocessor *pp) { _pp = pp; } - bool SeenEnd; - void setSourceManager(SourceManager * sm) { _sm = sm; } - void setPreprocessor (Preprocessor * pp) { _pp = pp; } +private: + SourceManager *_sm; + Preprocessor *_pp; - private: - - SourceManager * _sm; - Preprocessor * _pp; - - Replacements * Replace; - struct hipName N; - }; + Replacements *Replace; + struct hipName N; +}; class Cuda2HipCallback : public MatchFinder::MatchCallback { - public: - Cuda2HipCallback(Replacements *Replace, ast_matchers::MatchFinder *parent) - : Replace(Replace), owner(parent) {} +public: + Cuda2HipCallback(Replacements *Replace, ast_matchers::MatchFinder *parent) + : Replace(Replace), owner(parent) {} - void convertKernelDecl(const FunctionDecl * kernelDecl, const MatchFinder::MatchResult &Result) - { - SourceManager * SM = Result.SourceManager; - LangOptions DefaultLangOptions; + void convertKernelDecl(const FunctionDecl *kernelDecl, + const MatchFinder::MatchResult &Result) { + SourceManager *SM = Result.SourceManager; + LangOptions DefaultLangOptions; - SmallString<40> XStr; - raw_svector_ostream OS(XStr); - StringRef initialParamList; - OS << "hipLaunchParm lp"; - size_t replacementLength = OS.str().size(); - SourceLocation sl = kernelDecl->getNameInfo().getEndLoc(); - SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken(sl, clang::tok::l_paren, *SM, DefaultLangOptions, true); - DEBUG(dbgs() << kernelArgListStart.printToString(*SM)); - if (kernelDecl->getNumParams() > 0) { - const ParmVarDecl * pvdFirst = kernelDecl->getParamDecl(0); - const ParmVarDecl * pvdLast = kernelDecl->getParamDecl(kernelDecl->getNumParams() - 1); - SourceLocation kernelArgListStart(pvdFirst->getLocStart()); - SourceLocation kernelArgListEnd(pvdLast->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(kernelArgListEnd, 0, *SM, DefaultLangOptions); - size_t replacementLength = SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); - initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); - OS << ", " << initialParamList; - } - DEBUG(dbgs() << "initial paramlist: " << initialParamList << "\n"); - DEBUG(dbgs() << "new paramlist: " << OS.str() << "\n"); - Replacement Rep0(*(Result.SourceManager), kernelArgListStart, replacementLength, OS.str()); - Replace->insert(Rep0); + SmallString<40> XStr; + raw_svector_ostream OS(XStr); + StringRef initialParamList; + OS << "hipLaunchParm lp"; + size_t replacementLength = OS.str().size(); + SourceLocation sl = kernelDecl->getNameInfo().getEndLoc(); + SourceLocation kernelArgListStart = clang::Lexer::findLocationAfterToken( + sl, clang::tok::l_paren, *SM, DefaultLangOptions, true); + DEBUG(dbgs() << kernelArgListStart.printToString(*SM)); + if (kernelDecl->getNumParams() > 0) { + const ParmVarDecl *pvdFirst = kernelDecl->getParamDecl(0); + const ParmVarDecl *pvdLast = + kernelDecl->getParamDecl(kernelDecl->getNumParams() - 1); + SourceLocation kernelArgListStart(pvdFirst->getLocStart()); + SourceLocation kernelArgListEnd(pvdLast->getLocEnd()); + SourceLocation stop = clang::Lexer::getLocForEndOfToken( + kernelArgListEnd, 0, *SM, DefaultLangOptions); + size_t replacementLength = + SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); + initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), + replacementLength); + OS << ", " << initialParamList; + } + DEBUG(dbgs() << "initial paramlist: " << initialParamList << "\n" + << "new paramlist: " << OS.str() << "\n"); + Replacement Rep0(*(Result.SourceManager), kernelArgListStart, + replacementLength, OS.str()); + Replace->insert(Rep0); } void run(const MatchFinder::MatchResult &Result) override { - - SourceManager * SM = Result.SourceManager; + SourceManager *SM = Result.SourceManager; LangOptions DefaultLangOptions; - if (const CallExpr * call = Result.Nodes.getNodeAs("cudaCall")) - { - const FunctionDecl * funcDcl = call->getDirectCallee(); + if (const CallExpr *call = + Result.Nodes.getNodeAs("cudaCall")) { + const FunctionDecl *funcDcl = call->getDirectCallee(); StringRef name = funcDcl->getDeclName().getAsString(); if (N.cuda2hipRename.count(name)) { StringRef repName = N.cuda2hipRename[name]; SourceLocation sl = call->getLocStart(); - Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? - SM->getImmediateSpellingLoc(sl) : sl, name.size(), repName); + Replacement Rep(*SM, SM->isMacroArgExpansion(sl) + ? SM->getImmediateSpellingLoc(sl) + : sl, + name.size(), repName); Replace->insert(Rep); } } - if (const CUDAKernelCallExpr * launchKernel = Result.Nodes.getNodeAs("cudaLaunchKernel")) - { + if (const CUDAKernelCallExpr *launchKernel = + Result.Nodes.getNodeAs( + "cudaLaunchKernel")) { SmallString<40> XStr; raw_svector_ostream OS(XStr); StringRef calleeName; - const FunctionDecl * kernelDecl = launchKernel->getDirectCallee(); + const FunctionDecl *kernelDecl = launchKernel->getDirectCallee(); if (kernelDecl) { calleeName = kernelDecl->getName(); convertKernelDecl(kernelDecl, Result); - } - else { - const Expr * e = launchKernel->getCallee(); - if (const UnresolvedLookupExpr * ule = dyn_cast(e)) { + } else { + const Expr *e = launchKernel->getCallee(); + if (const UnresolvedLookupExpr *ule = + dyn_cast(e)) { calleeName = ule->getName().getAsIdentifierInfo()->getName(); - owner->addMatcher(functionTemplateDecl(hasName(calleeName)).bind("unresolvedTemplateName"), this); + owner->addMatcher(functionTemplateDecl(hasName(calleeName)) + .bind("unresolvedTemplateName"), + this); } } - XStr.clear(); - OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << calleeName << "), "; + OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << calleeName << "),"; - const CallExpr * config = launchKernel->getConfig(); + const CallExpr *config = launchKernel->getConfig(); DEBUG(dbgs() << "Kernel config arguments:" << "\n"); - for (unsigned argno = 0; argno < config->getNumArgs(); argno++) - { - const Expr * arg = config->getArg(argno); + for (unsigned argno = 0; argno < config->getNumArgs(); argno++) { + const Expr *arg = config->getArg(argno); if (!isa(arg)) { - const ParmVarDecl * pvd = config->getDirectCallee()->getParamDecl(argno); + const ParmVarDecl *pvd = + config->getDirectCallee()->getParamDecl(argno); SourceLocation sl(arg->getLocStart()); SourceLocation el(arg->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); - StringRef outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + SourceLocation stop = + clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + StringRef outs(SM->getCharacterData(sl), + SM->getCharacterData(stop) - SM->getCharacterData(sl)); DEBUG(dbgs() << "args[ " << argno << "]" << outs << " <" - << pvd->getType().getAsString() << ">" << "\n"); + << pvd->getType().getAsString() << ">" << "\n"); if (pvd->getType().getAsString().compare("dim3") == 0) OS << " dim3(" << outs << "),"; else @@ -485,50 +493,56 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { OS << " 0,"; } - for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) - { - const Expr * arg = launchKernel->getArg(argno); + for (unsigned argno = 0; argno < launchKernel->getNumArgs(); argno++) { + const Expr *arg = launchKernel->getArg(argno); SourceLocation sl(arg->getLocStart()); SourceLocation el(arg->getLocEnd()); - SourceLocation stop = clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); - std::string outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); + SourceLocation stop = + clang::Lexer::getLocForEndOfToken(el, 0, *SM, DefaultLangOptions); + std::string outs(SM->getCharacterData(sl), + SM->getCharacterData(stop) - SM->getCharacterData(sl)); DEBUG(dbgs() << outs << "\n"); OS << " " << outs << ","; } XStr.pop_back(); OS << ")"; - size_t length = SM->getCharacterData(clang::Lexer::getLocForEndOfToken(launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - - SM->getCharacterData(launchKernel->getLocStart()); + size_t length = + SM->getCharacterData(clang::Lexer::getLocForEndOfToken( + launchKernel->getLocEnd(), 0, *SM, DefaultLangOptions)) - + SM->getCharacterData(launchKernel->getLocStart()); Replacement Rep(*SM, launchKernel->getLocStart(), length, OS.str()); Replace->insert(Rep); - } + } - if (const FunctionTemplateDecl * templateDecl = Result.Nodes.getNodeAs("unresolvedTemplateName")) - { - FunctionDecl * kernelDecl = templateDecl->getTemplatedDecl(); + if (const FunctionTemplateDecl *templateDecl = + Result.Nodes.getNodeAs( + "unresolvedTemplateName")) { + FunctionDecl *kernelDecl = templateDecl->getTemplatedDecl(); convertKernelDecl(kernelDecl, Result); } - if (const MemberExpr * threadIdx = Result.Nodes.getNodeAs("cudaBuiltin")) - { - if (const OpaqueValueExpr * refBase = dyn_cast(threadIdx->getBase())) { - if (const DeclRefExpr * declRef = dyn_cast(refBase->getSourceExpr())) { - StringRef name = declRef->getDecl()->getName(); - StringRef memberName = threadIdx->getMemberDecl()->getName(); - size_t pos = memberName.find_first_not_of("__fetch_builtin_"); - memberName = memberName.slice(pos, memberName.size()); - SmallString<128> tmpData; - name = Twine(name+"."+memberName).toStringRef(tmpData); - StringRef repName = N.cuda2hipRename[name]; - SourceLocation sl = threadIdx->getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + if (const MemberExpr *threadIdx = + Result.Nodes.getNodeAs("cudaBuiltin")) { + if (const OpaqueValueExpr *refBase = + dyn_cast(threadIdx->getBase())) { + if (const DeclRefExpr *declRef = + dyn_cast(refBase->getSourceExpr())) { + StringRef name = declRef->getDecl()->getName(); + StringRef memberName = threadIdx->getMemberDecl()->getName(); + size_t pos = memberName.find_first_not_of("__fetch_builtin_"); + memberName = memberName.slice(pos, memberName.size()); + SmallString<128> tmpData; + name = Twine(name + "." + memberName).toStringRef(tmpData); + StringRef repName = N.cuda2hipRename[name]; + SourceLocation sl = threadIdx->getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); } - } - } + } + } - if (const DeclRefExpr * cudaEnumConstantRef = Result.Nodes.getNodeAs("cudaEnumConstantRef")) - { + if (const DeclRefExpr *cudaEnumConstantRef = + Result.Nodes.getNodeAs("cudaEnumConstantRef")) { StringRef name = cudaEnumConstantRef->getDecl()->getNameAsString(); StringRef repName = N.cuda2hipRename[name]; SourceLocation sl = cudaEnumConstantRef->getLocStart(); @@ -536,18 +550,22 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { Replace->insert(Rep); } - if (const VarDecl * cudaEnumConstantDecl = Result.Nodes.getNodeAs("cudaEnumConstantDecl")) - { - StringRef name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); + if (const VarDecl *cudaEnumConstantDecl = + Result.Nodes.getNodeAs("cudaEnumConstantDecl")) { + StringRef name = + cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); StringRef repName = N.cuda2hipRename[name]; SourceLocation sl = cudaEnumConstantDecl->getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); } - if (const VarDecl * cudaStructVar = Result.Nodes.getNodeAs("cudaStructVar")) - { - StringRef name = cudaStructVar->getType()->getAsStructureType()->getDecl()->getNameAsString(); + if (const VarDecl *cudaStructVar = + Result.Nodes.getNodeAs("cudaStructVar")) { + StringRef name = cudaStructVar->getType() + ->getAsStructureType() + ->getDecl() + ->getNameAsString(); StringRef repName = N.cuda2hipRename[name]; TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); @@ -555,9 +573,9 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { Replace->insert(Rep); } - if (const VarDecl * cudaStructVarPtr = Result.Nodes.getNodeAs("cudaStructVarPtr")) - { - const Type * t = cudaStructVarPtr->getType().getTypePtrOrNull(); + if (const VarDecl *cudaStructVarPtr = + Result.Nodes.getNodeAs("cudaStructVarPtr")) { + const Type *t = cudaStructVarPtr->getType().getTypePtrOrNull(); if (t) { StringRef name = t->getPointeeCXXRecordDecl()->getName(); StringRef repName = N.cuda2hipRename[name]; @@ -568,12 +586,11 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { } } - - if (const ParmVarDecl * cudaParamDecl = Result.Nodes.getNodeAs("cudaParamDecl")) - { + if (const ParmVarDecl *cudaParamDecl = + Result.Nodes.getNodeAs("cudaParamDecl")) { QualType QT = cudaParamDecl->getOriginalType().getUnqualifiedType(); StringRef name = QT.getAsString(); - const Type * t = QT.getTypePtr(); + const Type *t = QT.getTypePtr(); if (t->isStructureOrClassType()) { name = t->getAsCXXRecordDecl()->getName(); } @@ -584,14 +601,15 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { Replace->insert(Rep); } - if (const ParmVarDecl * cudaParamDeclPtr = Result.Nodes.getNodeAs("cudaParamDeclPtr")) - { - const Type * pt = cudaParamDeclPtr->getType().getTypePtrOrNull(); + if (const ParmVarDecl *cudaParamDeclPtr = + Result.Nodes.getNodeAs("cudaParamDeclPtr")) { + const Type *pt = cudaParamDeclPtr->getType().getTypePtrOrNull(); if (pt) { QualType QT = pt->getPointeeType(); - const Type * t = QT.getTypePtr(); - StringRef name = t->isStructureOrClassType()? - t->getAsCXXRecordDecl()->getName() : StringRef(QT.getAsString()); + const Type *t = QT.getTypePtr(); + StringRef name = t->isStructureOrClassType() + ? t->getAsCXXRecordDecl()->getName() + : StringRef(QT.getAsString()); StringRef repName = N.cuda2hipRename[name]; TypeLoc TL = cudaParamDeclPtr->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); @@ -600,20 +618,20 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { } } - - if (const StringLiteral * stringLiteral = Result.Nodes.getNodeAs("stringLiteral")) - { + if (const StringLiteral *stringLiteral = + Result.Nodes.getNodeAs("stringLiteral")) { if (stringLiteral->getCharByteWidth() == 1) { StringRef s = stringLiteral->getString(); processString(s, N, Replace, *SM, stringLiteral->getLocStart()); } } - if (const UnaryExprOrTypeTraitExpr * expr = Result.Nodes.getNodeAs("cudaStructSizeOf")) - { - TypeSourceInfo * typeInfo = expr->getArgumentTypeInfo(); + if (const UnaryExprOrTypeTraitExpr *expr = + Result.Nodes.getNodeAs( + "cudaStructSizeOf")) { + TypeSourceInfo *typeInfo = expr->getArgumentTypeInfo(); QualType QT = typeInfo->getType().getUnqualifiedType(); - const Type * type = QT.getTypePtr(); + const Type *type = QT.getTypePtr(); StringRef name = type->getAsCXXRecordDecl()->getName(); StringRef repName = N.cuda2hipRename[name]; TypeLoc TL = typeInfo->getTypeLoc(); @@ -623,27 +641,29 @@ class Cuda2HipCallback : public MatchFinder::MatchCallback { } } - private: +private: Replacements *Replace; - ast_matchers::MatchFinder * owner; + ast_matchers::MatchFinder *owner; struct hipName N; }; } // end anonymous namespace // Set up the command line options -static cl::OptionCategory ToolTemplateCategory("CUDA to HIP source translator options"); -static cl::extrahelp MoreHelp( " specify the path of source file\n\n" ); +static cl::OptionCategory + ToolTemplateCategory("CUDA to HIP source translator options"); +static cl::extrahelp MoreHelp(" specify the path of source file\n\n"); -static cl::opt -OutputFilename("o", cl::desc("Output filename"), cl::value_desc("filename"), cl::cat(ToolTemplateCategory)); - -//static cl::opt -//Debug("debug", cl::desc("Enable debug output"), cl::Hidden, cl::location(llvm::DebugFlag)); +static cl::opt OutputFilename("o", cl::desc("Output filename"), + cl::value_desc("filename"), + cl::cat(ToolTemplateCategory)); static cl::opt -Inplace("inplace", cl::desc("Modify input file inplace, replacing input with hipified output, save backup in .prehip file. " - "If .prehip file exists, use that as input to hip."), cl::value_desc("inplace"), cl::cat(ToolTemplateCategory)); + Inplace("inplace", + cl::desc("Modify input file inplace, replacing input with hipified " + "output, save backup in .prehip file. " + "If .prehip file exists, use that as input to hip."), + cl::value_desc("inplace"), cl::cat(ToolTemplateCategory)); int main(int argc, const char **argv) { @@ -651,7 +671,8 @@ int main(int argc, const char **argv) { int Result; - CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory, llvm::cl::Required); + CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory, + llvm::cl::Required); std::string dst = OutputFilename; std::vector fileSources = OptionsParser.getSourcePathList(); if (dst.empty()) { @@ -673,7 +694,7 @@ int main(int argc, const char **argv) { } std::ifstream source(fileSources[0], std::ios::binary); - std::ofstream dest(Inplace ? dst+".prehip" : dst, std::ios::binary); + std::ofstream dest(Inplace ? dst + ".prehip" : dst, std::ios::binary); dest << source.rdbuf(); source.close(); dest.close(); @@ -682,17 +703,49 @@ int main(int argc, const char **argv) { ast_matchers::MatchFinder Finder; Cuda2HipCallback Callback(&Tool.getReplacements(), &Finder); HipifyPPCallbacks PPCallbacks(&Tool.getReplacements()); - Finder.addMatcher(callExpr(isExpansionInMainFile(), callee(functionDecl(matchesName("cuda.*")))).bind("cudaCall"), &Callback); + Finder.addMatcher(callExpr(isExpansionInMainFile(), + callee(functionDecl(matchesName("cuda.*")))) + .bind("cudaCall"), + &Callback); Finder.addMatcher(cudaKernelCallExpr().bind("cudaLaunchKernel"), &Callback); - Finder.addMatcher(memberExpr(isExpansionInMainFile(), hasObjectExpression(hasType(cxxRecordDecl(matchesName("__cuda_builtin_"))))).bind("cudaBuiltin"), &Callback); - Finder.addMatcher(declRefExpr(isExpansionInMainFile(), to(enumConstantDecl(matchesName("cuda.*")))).bind("cudaEnumConstantRef"), &Callback); - Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))).bind("cudaEnumConstantDecl"), &Callback); - Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(cxxRecordDecl(matchesName("cuda.*")))).bind("cudaStructVar"), &Callback); - Finder.addMatcher(varDecl(isExpansionInMainFile(), hasType(pointsTo(cxxRecordDecl(matchesName("cuda.*"))))).bind("cudaStructVarPtr"), &Callback); - Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(namedDecl(matchesName("cuda.*")))).bind("cudaParamDecl"), &Callback); - Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), hasType(pointsTo(namedDecl(matchesName("cuda.*"))))).bind("cudaParamDeclPtr"), &Callback); - Finder.addMatcher(expr(isExpansionInMainFile(), sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration(cxxRecordDecl(matchesName("cuda.*"))))))).bind("cudaStructSizeOf"), &Callback); - Finder.addMatcher(stringLiteral(isExpansionInMainFile()).bind("stringLiteral"), &Callback); + Finder.addMatcher(memberExpr(isExpansionInMainFile(), + hasObjectExpression(hasType(cxxRecordDecl( + matchesName("__cuda_builtin_"))))) + .bind("cudaBuiltin"), + &Callback); + Finder.addMatcher(declRefExpr(isExpansionInMainFile(), + to(enumConstantDecl(matchesName("cuda.*")))) + .bind("cudaEnumConstantRef"), + &Callback); + Finder.addMatcher( + varDecl(isExpansionInMainFile(), hasType(enumDecl(matchesName("cuda.*")))) + .bind("cudaEnumConstantDecl"), + &Callback); + Finder.addMatcher(varDecl(isExpansionInMainFile(), + hasType(cxxRecordDecl(matchesName("cuda.*")))) + .bind("cudaStructVar"), + &Callback); + Finder.addMatcher( + varDecl(isExpansionInMainFile(), + hasType(pointsTo(cxxRecordDecl(matchesName("cuda.*"))))) + .bind("cudaStructVarPtr"), + &Callback); + Finder.addMatcher(parmVarDecl(isExpansionInMainFile(), + hasType(namedDecl(matchesName("cuda.*")))) + .bind("cudaParamDecl"), + &Callback); + Finder.addMatcher( + parmVarDecl(isExpansionInMainFile(), + hasType(pointsTo(namedDecl(matchesName("cuda.*"))))) + .bind("cudaParamDeclPtr"), + &Callback); + Finder.addMatcher(expr(isExpansionInMainFile(), + sizeOfExpr(hasArgumentOfType(recordType(hasDeclaration( + cxxRecordDecl(matchesName("cuda.*"))))))) + .bind("cudaStructSizeOf"), + &Callback); + Finder.addMatcher( + stringLiteral(isExpansionInMainFile()).bind("stringLiteral"), &Callback); auto action = newFrontendActionFactory(&Finder, &PPCallbacks); @@ -700,12 +753,13 @@ int main(int argc, const char **argv) { compilationStages.push_back("--cuda-host-only"); compilationStages.push_back("--cuda-device-only"); - for (auto Stage : compilationStages) - { - Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster(Stage, ArgumentInsertPosition::BEGIN)); + for (auto Stage : compilationStages) { + Tool.appendArgumentsAdjuster( + getInsertArgumentAdjuster(Stage, ArgumentInsertPosition::BEGIN)); Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster("-std=c++11")); #if defined(HIPIFY_CLANG_RES) - Tool.appendArgumentsAdjuster(getInsertArgumentAdjuster("-resource-dir=" HIPIFY_CLANG_RES)); + Tool.appendArgumentsAdjuster( + getInsertArgumentAdjuster("-resource-dir=" HIPIFY_CLANG_RES)); #endif // defined(HIPIFY_CLANG_HEADERS) Tool.appendArgumentsAdjuster(getClangSyntaxOnlyAdjuster()); Result = Tool.run(action.get()); @@ -717,8 +771,8 @@ int main(int argc, const char **argv) { IntrusiveRefCntPtr DiagOpts = new DiagnosticOptions(); TextDiagnosticPrinter DiagnosticPrinter(llvm::errs(), &*DiagOpts); DiagnosticsEngine Diagnostics( - IntrusiveRefCntPtr(new DiagnosticIDs()), - &*DiagOpts, &DiagnosticPrinter, false); + IntrusiveRefCntPtr(new DiagnosticIDs()), &*DiagOpts, + &DiagnosticPrinter, false); SourceManager Sources(Diagnostics, Tool.getFiles()); DEBUG(dbgs() << "Replacements collected by the tool:\n"); @@ -736,8 +790,7 @@ int main(int argc, const char **argv) { if (!Inplace) { size_t pos = dst.rfind(".cu"); - if (pos != std::string::npos) - { + if (pos != std::string::npos) { rename(dst.c_str(), dst.substr(0, pos).c_str()); } } From 64c4ca1cc63b9955f1acd731a0eaff6da3214728 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Thu, 24 Mar 2016 19:31:42 +0300 Subject: [PATCH 35/56] 1. added stubs for options -no-output, -print-stats 2. preparations for stats collection --- hipamd/src/Cuda2Hip.cpp | 311 ++++++++++++++++++++++------------------ 1 file changed, 174 insertions(+), 137 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index db8527835f..a78a35a3ab 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -55,183 +55,211 @@ using namespace llvm; #define DEBUG_TYPE "cuda2hip" namespace { -struct hipName { - hipName() { + +enum ConvTypes { + CONV_DEV = 0, + CONV_MEM, + CONV_KERN, + CONV_COORD_FUNC, + CONV_MATH_FUNC, + CONV_SPECIAL_FUNC, + CONV_STREAM, + CONV_EVENT, + CONV_ERR, + CONV_DEF, + CONV_TEX, + CONV_OTHER, + CONV_INC, + CONV_LAST +} ; + +struct cuda2hipMap { + cuda2hipMap() { // defines - cuda2hipRename["__CUDACC__"] = "__HIPCC__"; + cuda2hipRename["__CUDACC__"] = {"__HIPCC__", CONV_DEF}; // includes - cuda2hipRename["cuda_runtime.h"] = "hip_runtime.h"; - cuda2hipRename["cuda_runtime_api.h"] = "hip_runtime_api.h"; + cuda2hipRename["cuda_runtime.h"] = {"hip_runtime.h", CONV_INC}; + cuda2hipRename["cuda_runtime_api.h"] = {"hip_runtime_api.h", CONV_INC}; // Error codes and return types: - cuda2hipRename["cudaError_t"] = "hipError_t"; - cuda2hipRename["cudaError"] = "hipError"; - cuda2hipRename["cudaSuccess"] = "hipSuccess"; + cuda2hipRename["cudaError_t"] = {"hipError_t", CONV_ERR}; + cuda2hipRename["cudaError"] = {"hipError", CONV_ERR}; + cuda2hipRename["cudaSuccess"] = {"hipSuccess", CONV_ERR}; - cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; - cuda2hipRename["cudaErrorMemoryAllocation"] = "hipErrorMemoryAllocation"; - cuda2hipRename["cudaErrorMemoryFree"] = "hipErrorMemoryFree"; - cuda2hipRename["cudaErrorUnknownSymbol"] = "hipErrorUnknownSymbol"; - cuda2hipRename["cudaErrorOutOfResources"] = "hipErrorOutOfResources"; - cuda2hipRename["cudaErrorInvalidValue"] = "hipErrorInvalidValue"; + cuda2hipRename["cudaErrorUnknown"] = {"hipErrorUnknown", CONV_ERR}; + cuda2hipRename["cudaErrorMemoryAllocation"] = {"hipErrorMemoryAllocation", CONV_ERR}; + cuda2hipRename["cudaErrorMemoryFree"] = {"hipErrorMemoryFree", CONV_ERR}; + cuda2hipRename["cudaErrorUnknownSymbol"] = {"hipErrorUnknownSymbol", CONV_ERR}; + cuda2hipRename["cudaErrorOutOfResources"] = {"hipErrorOutOfResources", CONV_ERR}; + cuda2hipRename["cudaErrorInvalidValue"] = {"hipErrorInvalidValue", CONV_ERR}; cuda2hipRename["cudaErrorInvalidResourceHandle"] = - "hipErrorInvalidResourceHandle"; - cuda2hipRename["cudaErrorInvalidDevice"] = "hipErrorInvalidDevice"; - cuda2hipRename["cudaErrorNoDevice"] = "hipErrorNoDevice"; - cuda2hipRename["cudaErrorNotReady"] = "hipErrorNotReady"; - cuda2hipRename["cudaErrorUnknown"] = "hipErrorUnknown"; + {"hipErrorInvalidResourceHandle", CONV_ERR}; + cuda2hipRename["cudaErrorInvalidDevice"] = {"hipErrorInvalidDevice", CONV_ERR}; + cuda2hipRename["cudaErrorNoDevice"] = {"hipErrorNoDevice", CONV_ERR}; + cuda2hipRename["cudaErrorNotReady"] = {"hipErrorNotReady", CONV_ERR}; + cuda2hipRename["cudaErrorUnknown"] = {"hipErrorUnknown", CONV_ERR}; // error APIs: - cuda2hipRename["cudaGetLastError"] = "hipGetLastError"; - cuda2hipRename["cudaPeekAtLastError"] = "hipPeekAtLastError"; - cuda2hipRename["cudaGetErrorName"] = "hipGetErrorName"; - cuda2hipRename["cudaGetErrorString"] = "hipGetErrorString"; + cuda2hipRename["cudaGetLastError"] = {"hipGetLastError", CONV_ERR}; + cuda2hipRename["cudaPeekAtLastError"] = {"hipPeekAtLastError", CONV_ERR}; + cuda2hipRename["cudaGetErrorName"] = {"hipGetErrorName", CONV_ERR}; + cuda2hipRename["cudaGetErrorString"] = {"hipGetErrorString", CONV_ERR}; // Memcpy - cuda2hipRename["cudaMemcpy"] = "hipMemcpy"; - cuda2hipRename["cudaMemcpyHostToHost"] = "hipMemcpyHostToHost"; - cuda2hipRename["cudaMemcpyHostToDevice"] = "hipMemcpyHostToDevice"; - cuda2hipRename["cudaMemcpyDeviceToHost"] = "hipMemcpyDeviceToHost"; - cuda2hipRename["cudaMemcpyDeviceToDevice"] = "hipMemcpyDeviceToDevice"; - cuda2hipRename["cudaMemcpyDefault"] = "hipMemcpyDefault"; - cuda2hipRename["cudaMemcpyToSymbol"] = "hipMemcpyToSymbol"; - cuda2hipRename["cudaMemset"] = "hipMemset"; - cuda2hipRename["cudaMemsetAsync"] = "hipMemsetAsync"; - cuda2hipRename["cudaMemcpyAsync"] = "hipMemcpyAsync"; - cuda2hipRename["cudaMemGetInfo"] = "hipMemGetInfo"; - cuda2hipRename["cudaMemcpyKind"] = "hipMemcpyKind"; + cuda2hipRename["cudaMemcpy"] = {"hipMemcpy", CONV_MEM}; + cuda2hipRename["cudaMemcpyHostToHost"] = {"hipMemcpyHostToHost", CONV_MEM}; + cuda2hipRename["cudaMemcpyHostToDevice"] = {"hipMemcpyHostToDevice", CONV_MEM}; + cuda2hipRename["cudaMemcpyDeviceToHost"] = {"hipMemcpyDeviceToHost", CONV_MEM}; + cuda2hipRename["cudaMemcpyDeviceToDevice"] = {"hipMemcpyDeviceToDevice", CONV_MEM}; + cuda2hipRename["cudaMemcpyDefault"] = {"hipMemcpyDefault", CONV_MEM}; + cuda2hipRename["cudaMemcpyToSymbol"] = {"hipMemcpyToSymbol", CONV_MEM}; + cuda2hipRename["cudaMemset"] = {"hipMemset", CONV_MEM}; + cuda2hipRename["cudaMemsetAsync"] = {"hipMemsetAsync", CONV_MEM}; + cuda2hipRename["cudaMemcpyAsync"] = {"hipMemcpyAsync", CONV_MEM}; + cuda2hipRename["cudaMemGetInfo"] = {"hipMemGetInfo", CONV_MEM}; + cuda2hipRename["cudaMemcpyKind"] = {"hipMemcpyKind", CONV_MEM}; // Memory management : - cuda2hipRename["cudaMalloc"] = "hipMalloc"; - cuda2hipRename["cudaMallocHost"] = "hipHostAlloc"; - cuda2hipRename["cudaFree"] = "hipFree"; - cuda2hipRename["cudaFreeHost"] = "hipHostFree"; + cuda2hipRename["cudaMalloc"] = {"hipMalloc", CONV_MEM}; + cuda2hipRename["cudaMallocHost"] = {"hipHostAlloc", CONV_MEM}; + cuda2hipRename["cudaFree"] = {"hipFree", CONV_MEM}; + cuda2hipRename["cudaFreeHost"] = {"hipHostFree", CONV_MEM}; // Coordinate Indexing and Dimensions: - cuda2hipRename["threadIdx.x"] = "hipThreadIdx_x"; - cuda2hipRename["threadIdx.y"] = "hipThreadIdx_y"; - cuda2hipRename["threadIdx.z"] = "hipThreadIdx_z"; + cuda2hipRename["threadIdx.x"] = {"hipThreadIdx_x", CONV_COORD_FUNC}; + cuda2hipRename["threadIdx.y"] = {"hipThreadIdx_y", CONV_COORD_FUNC}; + cuda2hipRename["threadIdx.z"] = {"hipThreadIdx_z", CONV_COORD_FUNC}; - cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; - cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; - cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; + cuda2hipRename["blockIdx.x"] = {"hipBlockIdx_x", CONV_COORD_FUNC}; + cuda2hipRename["blockIdx.y"] = {"hipBlockIdx_y", CONV_COORD_FUNC}; + cuda2hipRename["blockIdx.z"] = {"hipBlockIdx_z", CONV_COORD_FUNC}; - cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; - cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; - cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; + cuda2hipRename["blockDim.x"] = {"hipBlockDim_x", CONV_COORD_FUNC}; + cuda2hipRename["blockDim.y"] = {"hipBlockDim_y", CONV_COORD_FUNC}; + cuda2hipRename["blockDim.z"] = {"hipBlockDim_z", CONV_COORD_FUNC}; - cuda2hipRename["gridDim.x"] = "hipGridDim_x"; - cuda2hipRename["gridDim.y"] = "hipGridDim_y"; - cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + cuda2hipRename["gridDim.x"] = {"hipGridDim_x", CONV_COORD_FUNC}; + cuda2hipRename["gridDim.y"] = {"hipGridDim_y", CONV_COORD_FUNC}; + cuda2hipRename["gridDim.z"] = {"hipGridDim_z", CONV_COORD_FUNC}; - cuda2hipRename["blockIdx.x"] = "hipBlockIdx_x"; - cuda2hipRename["blockIdx.y"] = "hipBlockIdx_y"; - cuda2hipRename["blockIdx.z"] = "hipBlockIdx_z"; + cuda2hipRename["blockIdx.x"] = {"hipBlockIdx_x", CONV_COORD_FUNC}; + cuda2hipRename["blockIdx.y"] = {"hipBlockIdx_y", CONV_COORD_FUNC}; + cuda2hipRename["blockIdx.z"] = {"hipBlockIdx_z", CONV_COORD_FUNC}; - cuda2hipRename["blockDim.x"] = "hipBlockDim_x"; - cuda2hipRename["blockDim.y"] = "hipBlockDim_y"; - cuda2hipRename["blockDim.z"] = "hipBlockDim_z"; + cuda2hipRename["blockDim.x"] = {"hipBlockDim_x", CONV_COORD_FUNC}; + cuda2hipRename["blockDim.y"] = {"hipBlockDim_y", CONV_COORD_FUNC}; + cuda2hipRename["blockDim.z"] = {"hipBlockDim_z", CONV_COORD_FUNC}; - cuda2hipRename["gridDim.x"] = "hipGridDim_x"; - cuda2hipRename["gridDim.y"] = "hipGridDim_y"; - cuda2hipRename["gridDim.z"] = "hipGridDim_z"; + cuda2hipRename["gridDim.x"] = {"hipGridDim_x", CONV_COORD_FUNC}; + cuda2hipRename["gridDim.y"] = {"hipGridDim_y", CONV_COORD_FUNC}; + cuda2hipRename["gridDim.z"] = {"hipGridDim_z", CONV_COORD_FUNC}; - cuda2hipRename["warpSize"] = "hipWarpSize"; + cuda2hipRename["warpSize"] = {"hipWarpSize", CONV_SPECIAL_FUNC}; // Events - cuda2hipRename["cudaEvent_t"] = "hipEvent_t"; - cuda2hipRename["cudaEventCreate"] = "hipEventCreate"; - cuda2hipRename["cudaEventCreateWithFlags"] = "hipEventCreateWithFlags"; - cuda2hipRename["cudaEventDestroy"] = "hipEventDestroy"; - cuda2hipRename["cudaEventRecord"] = "hipEventRecord"; - cuda2hipRename["cudaEventElapsedTime"] = "hipEventElapsedTime"; - cuda2hipRename["cudaEventSynchronize"] = "hipEventSynchronize"; + cuda2hipRename["cudaEvent_t"] = {"hipEvent_t", CONV_EVENT}; + cuda2hipRename["cudaEventCreate"] = {"hipEventCreate", CONV_EVENT}; + cuda2hipRename["cudaEventCreateWithFlags"] = {"hipEventCreateWithFlags", CONV_EVENT}; + cuda2hipRename["cudaEventDestroy"] = {"hipEventDestroy", CONV_EVENT}; + cuda2hipRename["cudaEventRecord"] = {"hipEventRecord", CONV_EVENT}; + cuda2hipRename["cudaEventElapsedTime"] = {"hipEventElapsedTime", CONV_EVENT}; + cuda2hipRename["cudaEventSynchronize"] = {"hipEventSynchronize", CONV_EVENT}; // Streams - cuda2hipRename["cudaStream_t"] = "hipStream_t"; - cuda2hipRename["cudaStreamCreate"] = "hipStreamCreate"; - cuda2hipRename["cudaStreamCreateWithFlags"] = "hipStreamCreateWithFlags"; - cuda2hipRename["cudaStreamDestroy"] = "hipStreamDestroy"; - cuda2hipRename["cudaStreamWaitEvent"] = "hipStreamWaitEven"; - cuda2hipRename["cudaStreamSynchronize"] = "hipStreamSynchronize"; - cuda2hipRename["cudaStreamDefault"] = "hipStreamDefault"; - cuda2hipRename["cudaStreamNonBlocking"] = "hipStreamNonBlocking"; + cuda2hipRename["cudaStream_t"] = {"hipStream_t", CONV_STREAM}; + cuda2hipRename["cudaStreamCreate"] = {"hipStreamCreate", CONV_STREAM}; + cuda2hipRename["cudaStreamCreateWithFlags"] = {"hipStreamCreateWithFlags", CONV_STREAM}; + cuda2hipRename["cudaStreamDestroy"] = {"hipStreamDestroy", CONV_STREAM}; + cuda2hipRename["cudaStreamWaitEvent"] = {"hipStreamWaitEven", CONV_STREAM}; + cuda2hipRename["cudaStreamSynchronize"] = {"hipStreamSynchronize", CONV_STREAM}; + cuda2hipRename["cudaStreamDefault"] = {"hipStreamDefault", CONV_STREAM}; + cuda2hipRename["cudaStreamNonBlocking"] = {"hipStreamNonBlocking", CONV_STREAM}; // Other synchronization - cuda2hipRename["cudaDeviceSynchronize"] = "hipDeviceSynchronize"; + cuda2hipRename["cudaDeviceSynchronize"] = {"hipDeviceSynchronize", CONV_DEV}; cuda2hipRename["cudaThreadSynchronize"] = - "hipDeviceSynchronize"; // translate deprecated cudaThreadSynchronize - cuda2hipRename["cudaDeviceReset"] = "hipDeviceReset"; + {"hipDeviceSynchronize", CONV_DEV}; // translate deprecated cudaThreadSynchronize + cuda2hipRename["cudaDeviceReset"] = {"hipDeviceReset", CONV_DEV}; cuda2hipRename["cudaThreadExit"] = - "hipDeviceReset"; // translate deprecated cudaThreadExit - cuda2hipRename["cudaSetDevice"] = "hipSetDevice"; - cuda2hipRename["cudaGetDevice"] = "hipGetDevice"; + {"hipDeviceReset", CONV_DEV}; // translate deprecated cudaThreadExit + cuda2hipRename["cudaSetDevice"] = {"hipSetDevice", CONV_DEV}; + cuda2hipRename["cudaGetDevice"] = {"hipGetDevice", CONV_DEV}; + // Attribute + cuda2hipRename["bcudaDeviceAttr"] = {"hipDeviceAttribute_t", CONV_DEV}; + cuda2hipRename["bcudaDeviceGetAttribute"] = {"hipDeviceGetAttribute", CONV_DEV}; + // Device - cuda2hipRename["cudaDeviceProp"] = "hipDeviceProp_t"; - cuda2hipRename["cudaGetDeviceProperties"] = "hipDeviceGetProperties"; + cuda2hipRename["cudaDeviceProp"] = {"hipDeviceProp_t", CONV_DEV}; + cuda2hipRename["cudaGetDeviceProperties"] = {"hipDeviceGetProperties", CONV_DEV}; // Cache config - cuda2hipRename["cudaDeviceSetCacheConfig"] = "hipDeviceSetCacheConfig"; + cuda2hipRename["cudaDeviceSetCacheConfig"] = {"hipDeviceSetCacheConfig", CONV_DEV}; cuda2hipRename["cudaThreadSetCacheConfig"] = - "hipDeviceSetCacheConfig"; // translate deprecated - cuda2hipRename["cudaDeviceGetCacheConfig"] = "hipDeviceGetCacheConfig"; + {"hipDeviceSetCacheConfig", CONV_DEV}; // translate deprecated + cuda2hipRename["cudaDeviceGetCacheConfig"] = {"hipDeviceGetCacheConfig", CONV_DEV}; cuda2hipRename["cudaThreadGetCacheConfig"] = - "hipDeviceGetCacheConfig"; // translate deprecated - cuda2hipRename["cudaFuncCache"] = "hipFuncCache"; - cuda2hipRename["cudaFuncCachePreferNone"] = "hipFuncCachePreferNone"; - cuda2hipRename["cudaFuncCachePreferShared"] = "hipFuncCachePreferShared"; - cuda2hipRename["cudaFuncCachePreferL1"] = "hipFuncCachePreferL1"; - cuda2hipRename["cudaFuncCachePreferEqual"] = "hipFuncCachePreferEqual"; + {"hipDeviceGetCacheConfig", CONV_DEV}; // translate deprecated + cuda2hipRename["cudaFuncCache"] = {"hipFuncCache", CONV_DEV}; + cuda2hipRename["cudaFuncCachePreferNone"] = {"hipFuncCachePreferNone", CONV_DEV}; + cuda2hipRename["cudaFuncCachePreferShared"] = {"hipFuncCachePreferShared", CONV_DEV}; + cuda2hipRename["cudaFuncCachePreferL1"] = {"hipFuncCachePreferL1", CONV_DEV}; + cuda2hipRename["cudaFuncCachePreferEqual"] = {"hipFuncCachePreferEqual", CONV_DEV}; // function - cuda2hipRename["cudaFuncSetCacheConfig"] = "hipFuncSetCacheConfig"; + cuda2hipRename["cudaFuncSetCacheConfig"] = {"hipFuncSetCacheConfig", CONV_DEV}; - cuda2hipRename["cudaDriverGetVersion"] = "hipDriverGetVersion"; - cuda2hipRename["cudaRuntimeGetVersion"] = "hipRuntimeGetVersion"; + cuda2hipRename["cudaDriverGetVersion"] = {"hipDriverGetVersion", CONV_DEV}; +// cuda2hipRename["cudaRuntimeGetVersion"] = {"hipRuntimeGetVersion", CONV_DEV}; // Peer2Peer - cuda2hipRename["cudaDeviceCanAccessPeer"] = "hipDeviceCanAccessPeer"; + cuda2hipRename["cudaDeviceCanAccessPeer"] = {"hipDeviceCanAccessPeer", CONV_DEV}; cuda2hipRename["cudaDeviceDisablePeerAccess"] = - "hipDeviceDisablePeerAccess"; - cuda2hipRename["cudaDeviceEnablePeerAccess"] = "hipDeviceEnablePeerAccess"; - cuda2hipRename["cudaMemcpyPeerAsync"] = "hipMemcpyPeerAsync"; - cuda2hipRename["cudaMemcpyPeer"] = "hipMemcpyPeer"; + {"hipDeviceDisablePeerAccess", CONV_DEV}; + cuda2hipRename["cudaDeviceEnablePeerAccess"] = {"hipDeviceEnablePeerAccess", CONV_DEV}; + cuda2hipRename["cudaMemcpyPeerAsync"] = {"hipMemcpyPeerAsync", CONV_MEM}; + cuda2hipRename["cudaMemcpyPeer"] = {"hipMemcpyPeer", CONV_MEM}; // Shared mem: cuda2hipRename["cudaDeviceSetSharedMemConfig"] = - "hipDeviceSetSharedMemConfig"; + {"hipDeviceSetSharedMemConfig", CONV_DEV}; cuda2hipRename["cudaThreadSetSharedMemConfig"] = - "hipDeviceSetSharedMemConfig"; // translate deprecated + {"hipDeviceSetSharedMemConfig", CONV_DEV}; // translate deprecated cuda2hipRename["cudaDeviceGetSharedMemConfig"] = - "hipDeviceGetSharedMemConfig"; + {"hipDeviceGetSharedMemConfig", CONV_DEV}; cuda2hipRename["cudaThreadGetSharedMemConfig"] = - "hipDeviceGetSharedMemConfig"; // translate deprecated - cuda2hipRename["cudaSharedMemConfig"] = "hipSharedMemConfig"; + {"hipDeviceGetSharedMemConfig", CONV_DEV}; // translate deprecated + cuda2hipRename["cudaSharedMemConfig"] = {"hipSharedMemConfig", CONV_DEV}; cuda2hipRename["cudaSharedMemBankSizeDefault"] = - "hipSharedMemBankSizeDefault"; + {"hipSharedMemBankSizeDefault", CONV_DEV}; cuda2hipRename["cudaSharedMemBankSizeFourByte"] = - "hipSharedMemBankSizeFourByte"; + {"hipSharedMemBankSizeFourByte", CONV_DEV}; cuda2hipRename["cudaSharedMemBankSizeEightByte"] = - "hipSharedMemBankSizeEightByte"; + {"hipSharedMemBankSizeEightByte", CONV_DEV}; - cuda2hipRename["cudaGetDeviceCount"] = "hipGetDeviceCount"; + cuda2hipRename["cudaGetDeviceCount"] = {"hipGetDeviceCount", CONV_DEV}; // Profiler // cuda2hipRename["cudaProfilerInitialize"] = "hipProfilerInitialize"; // // see if these are called anywhere. - cuda2hipRename["cudaProfilerStart"] = "hipProfilerStart"; - cuda2hipRename["cudaProfilerStop"] = "hipProfilerStop"; + cuda2hipRename["cudaProfilerStart"] = {"hipProfilerStart", CONV_OTHER}; + cuda2hipRename["cudaProfilerStop"] = {"hipProfilerStop", CONV_OTHER}; - cuda2hipRename["cudaChannelFormatDesc"] = "hipChannelFormatDesc"; - cuda2hipRename["cudaFilterModePoint"] = "hipFilterModePoint"; - cuda2hipRename["cudaReadModeElementType"] = "hipReadModeElementType"; + cuda2hipRename["cudaChannelFormatDesc"] = {"hipChannelFormatDesc", CONV_TEX}; + cuda2hipRename["cudaFilterModePoint"] = {"hipFilterModePoint", CONV_TEX}; + cuda2hipRename["cudaReadModeElementType"] = {"hipReadModeElementType", CONV_TEX}; - cuda2hipRename["cudaCreateChannelDesc"] = "hipCreateChannelDesc"; - cuda2hipRename["cudaBindTexture"] = "hipBindTexture"; - cuda2hipRename["cudaUnbindTexture"] = "hipUnbindTexture"; + cuda2hipRename["cudaCreateChannelDesc"] = {"hipCreateChannelDesc", CONV_TEX}; + cuda2hipRename["cudaBindTexture"] = {"hipBindTexture", CONV_TEX}; + cuda2hipRename["cudaUnbindTexture"] = {"hipUnbindTexture", CONV_TEX}; } - DenseMap cuda2hipRename; + + struct HipNames { + StringRef hipName; + ConvTypes countType; + }; + + SmallDenseMap cuda2hipRename; }; StringRef unquoteStr(StringRef s) { @@ -240,13 +268,13 @@ StringRef unquoteStr(StringRef s) { return s; } -void processString(StringRef s, struct hipName &map, Replacements *Replace, +static void processString(StringRef s, struct cuda2hipMap &map, Replacements *Replace, SourceManager &SM, SourceLocation start) { size_t begin = 0; while ((begin = s.find("cuda", begin)) != StringRef::npos) { const size_t end = s.find_first_of(" ", begin + 4); StringRef name = s.slice(begin, end); - StringRef repName = map.cuda2hipRename[name]; + StringRef repName = map.cuda2hipRename[name].hipName; if (!repName.empty()) { SourceLocation sl = start.getLocWithOffset(begin + 1); Replacement Rep(SM, sl, name.size(), repName); @@ -283,7 +311,7 @@ struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { if (_sm->isWrittenInMainFile(hash_loc)) { if (is_angled) { if (N.cuda2hipRename.count(file_name)) { - StringRef repName = N.cuda2hipRename[file_name]; + StringRef repName = N.cuda2hipRename[file_name].hipName; DEBUG(dbgs() << "Include file found: " << file_name << "\n" << "SourceLocation:" << filename_range.getBegin().printToString(*_sm) << "\n" @@ -309,7 +337,7 @@ struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { if (T.isAnyIdentifier()) { StringRef name = T.getIdentifierInfo()->getName(); if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; SourceLocation sl = T.getLocation(); DEBUG(dbgs() << "Identifier " << name << " found in definition of macro " @@ -353,7 +381,7 @@ struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { if (tok.isAnyIdentifier()) { StringRef name = tok.getIdentifierInfo()->getName(); if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; DEBUG(dbgs() << "Identifier " << name << " found as an actual argument in expansion of macro " << macroName << "\n" @@ -383,7 +411,7 @@ private: Preprocessor *_pp; Replacements *Replace; - struct hipName N; + struct cuda2hipMap N; }; class Cuda2HipCallback : public MatchFinder::MatchCallback { @@ -435,7 +463,7 @@ public: const FunctionDecl *funcDcl = call->getDirectCallee(); StringRef name = funcDcl->getDeclName().getAsString(); if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; SourceLocation sl = call->getLocStart(); Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? SM->getImmediateSpellingLoc(sl) @@ -533,7 +561,7 @@ public: memberName = memberName.slice(pos, memberName.size()); SmallString<128> tmpData; name = Twine(name + "." + memberName).toStringRef(tmpData); - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; SourceLocation sl = threadIdx->getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); @@ -544,7 +572,7 @@ public: if (const DeclRefExpr *cudaEnumConstantRef = Result.Nodes.getNodeAs("cudaEnumConstantRef")) { StringRef name = cudaEnumConstantRef->getDecl()->getNameAsString(); - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; SourceLocation sl = cudaEnumConstantRef->getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); @@ -554,7 +582,7 @@ public: Result.Nodes.getNodeAs("cudaEnumConstantDecl")) { StringRef name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; SourceLocation sl = cudaEnumConstantDecl->getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); Replace->insert(Rep); @@ -566,7 +594,7 @@ public: ->getAsStructureType() ->getDecl() ->getNameAsString(); - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); @@ -578,7 +606,7 @@ public: const Type *t = cudaStructVarPtr->getType().getTypePtrOrNull(); if (t) { StringRef name = t->getPointeeCXXRecordDecl()->getName(); - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; TypeLoc TL = cudaStructVarPtr->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); @@ -594,7 +622,7 @@ public: if (t->isStructureOrClassType()) { name = t->getAsCXXRecordDecl()->getName(); } - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; TypeLoc TL = cudaParamDecl->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); @@ -610,7 +638,7 @@ public: StringRef name = t->isStructureOrClassType() ? t->getAsCXXRecordDecl()->getName() : StringRef(QT.getAsString()); - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; TypeLoc TL = cudaParamDeclPtr->getTypeSourceInfo()->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); @@ -633,7 +661,7 @@ public: QualType QT = typeInfo->getType().getUnqualifiedType(); const Type *type = QT.getTypePtr(); StringRef name = type->getAsCXXRecordDecl()->getName(); - StringRef repName = N.cuda2hipRename[name]; + StringRef repName = N.cuda2hipRename[name].hipName; TypeLoc TL = typeInfo->getTypeLoc(); SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); Replacement Rep(*SM, sl, name.size(), repName); @@ -644,7 +672,7 @@ public: private: Replacements *Replace; ast_matchers::MatchFinder *owner; - struct hipName N; + struct cuda2hipMap N; }; } // end anonymous namespace @@ -661,10 +689,18 @@ static cl::opt OutputFilename("o", cl::desc("Output filename"), static cl::opt Inplace("inplace", cl::desc("Modify input file inplace, replacing input with hipified " - "output, save backup in .prehip file. " - "If .prehip file exists, use that as input to hip."), + "output, save backup in .prehip file. "), cl::value_desc("inplace"), cl::cat(ToolTemplateCategory)); +static cl::opt + NoOutput("no-output", + cl::desc("don't write any translated output to stdout"), + cl::value_desc("no-output"), cl::cat(ToolTemplateCategory)); +static cl::opt + PrintStats("print-stats", + cl::desc("print the command-line, like a header"), + cl::value_desc("print-stats"), cl::cat(ToolTemplateCategory)); + int main(int argc, const char **argv) { llvm::sys::PrintStackTraceOnErrorSignal(); @@ -693,6 +729,7 @@ int main(int argc, const char **argv) { dst += ".cu"; } + // copy source file since tooling makes changes "inplace" std::ifstream source(fileSources[0], std::ios::binary); std::ofstream dest(Inplace ? dst + ".prehip" : dst, std::ios::binary); dest << source.rdbuf(); From 021138a9db939db7f6b08c97d8428fff60f084b2 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Fri, 25 Mar 2016 18:28:37 +0300 Subject: [PATCH 36/56] implemented -print-stats option, minor cleanup & optimizations --- hipamd/src/Cuda2Hip.cpp | 364 +++++++++++++++++++++++++--------------- hipamd/test/axpy.cu | 2 +- 2 files changed, 234 insertions(+), 132 deletions(-) diff --git a/hipamd/src/Cuda2Hip.cpp b/hipamd/src/Cuda2Hip.cpp index a78a35a3ab..65c051ec04 100644 --- a/hipamd/src/Cuda2Hip.cpp +++ b/hipamd/src/Cuda2Hip.cpp @@ -54,8 +54,6 @@ using namespace llvm; #define DEBUG_TYPE "cuda2hip" -namespace { - enum ConvTypes { CONV_DEV = 0, CONV_MEM, @@ -69,9 +67,17 @@ enum ConvTypes { CONV_DEF, CONV_TEX, CONV_OTHER, - CONV_INC, + CONV_INCLUDE, + CONV_LITERAL, CONV_LAST -} ; +}; + +const char *counterNames[ConvTypes::CONV_LAST] = { + "dev", "mem", "kern", "coord_func", "math_func", + "special_func", "stream", "event", "err", "def", + "tex", "other", "include", "literal"}; + +namespace { struct cuda2hipMap { cuda2hipMap() { @@ -79,8 +85,8 @@ struct cuda2hipMap { cuda2hipRename["__CUDACC__"] = {"__HIPCC__", CONV_DEF}; // includes - cuda2hipRename["cuda_runtime.h"] = {"hip_runtime.h", CONV_INC}; - cuda2hipRename["cuda_runtime_api.h"] = {"hip_runtime_api.h", CONV_INC}; + cuda2hipRename["cuda_runtime.h"] = {"hip_runtime.h", CONV_INCLUDE}; + cuda2hipRename["cuda_runtime_api.h"] = {"hip_runtime_api.h", CONV_INCLUDE}; // Error codes and return types: cuda2hipRename["cudaError_t"] = {"hipError_t", CONV_ERR}; @@ -88,14 +94,19 @@ struct cuda2hipMap { cuda2hipRename["cudaSuccess"] = {"hipSuccess", CONV_ERR}; cuda2hipRename["cudaErrorUnknown"] = {"hipErrorUnknown", CONV_ERR}; - cuda2hipRename["cudaErrorMemoryAllocation"] = {"hipErrorMemoryAllocation", CONV_ERR}; + cuda2hipRename["cudaErrorMemoryAllocation"] = {"hipErrorMemoryAllocation", + CONV_ERR}; cuda2hipRename["cudaErrorMemoryFree"] = {"hipErrorMemoryFree", CONV_ERR}; - cuda2hipRename["cudaErrorUnknownSymbol"] = {"hipErrorUnknownSymbol", CONV_ERR}; - cuda2hipRename["cudaErrorOutOfResources"] = {"hipErrorOutOfResources", CONV_ERR}; - cuda2hipRename["cudaErrorInvalidValue"] = {"hipErrorInvalidValue", CONV_ERR}; - cuda2hipRename["cudaErrorInvalidResourceHandle"] = - {"hipErrorInvalidResourceHandle", CONV_ERR}; - cuda2hipRename["cudaErrorInvalidDevice"] = {"hipErrorInvalidDevice", CONV_ERR}; + cuda2hipRename["cudaErrorUnknownSymbol"] = {"hipErrorUnknownSymbol", + CONV_ERR}; + cuda2hipRename["cudaErrorOutOfResources"] = {"hipErrorOutOfResources", + CONV_ERR}; + cuda2hipRename["cudaErrorInvalidValue"] = {"hipErrorInvalidValue", + CONV_ERR}; + cuda2hipRename["cudaErrorInvalidResourceHandle"] = { + "hipErrorInvalidResourceHandle", CONV_ERR}; + cuda2hipRename["cudaErrorInvalidDevice"] = {"hipErrorInvalidDevice", + CONV_ERR}; cuda2hipRename["cudaErrorNoDevice"] = {"hipErrorNoDevice", CONV_ERR}; cuda2hipRename["cudaErrorNotReady"] = {"hipErrorNotReady", CONV_ERR}; cuda2hipRename["cudaErrorUnknown"] = {"hipErrorUnknown", CONV_ERR}; @@ -109,9 +120,12 @@ struct cuda2hipMap { // Memcpy cuda2hipRename["cudaMemcpy"] = {"hipMemcpy", CONV_MEM}; cuda2hipRename["cudaMemcpyHostToHost"] = {"hipMemcpyHostToHost", CONV_MEM}; - cuda2hipRename["cudaMemcpyHostToDevice"] = {"hipMemcpyHostToDevice", CONV_MEM}; - cuda2hipRename["cudaMemcpyDeviceToHost"] = {"hipMemcpyDeviceToHost", CONV_MEM}; - cuda2hipRename["cudaMemcpyDeviceToDevice"] = {"hipMemcpyDeviceToDevice", CONV_MEM}; + cuda2hipRename["cudaMemcpyHostToDevice"] = {"hipMemcpyHostToDevice", + CONV_MEM}; + cuda2hipRename["cudaMemcpyDeviceToHost"] = {"hipMemcpyDeviceToHost", + CONV_MEM}; + cuda2hipRename["cudaMemcpyDeviceToDevice"] = {"hipMemcpyDeviceToDevice", + CONV_MEM}; cuda2hipRename["cudaMemcpyDefault"] = {"hipMemcpyDefault", CONV_MEM}; cuda2hipRename["cudaMemcpyToSymbol"] = {"hipMemcpyToSymbol", CONV_MEM}; cuda2hipRename["cudaMemset"] = {"hipMemset", CONV_MEM}; @@ -160,82 +174,102 @@ struct cuda2hipMap { // Events cuda2hipRename["cudaEvent_t"] = {"hipEvent_t", CONV_EVENT}; cuda2hipRename["cudaEventCreate"] = {"hipEventCreate", CONV_EVENT}; - cuda2hipRename["cudaEventCreateWithFlags"] = {"hipEventCreateWithFlags", CONV_EVENT}; + cuda2hipRename["cudaEventCreateWithFlags"] = {"hipEventCreateWithFlags", + CONV_EVENT}; cuda2hipRename["cudaEventDestroy"] = {"hipEventDestroy", CONV_EVENT}; cuda2hipRename["cudaEventRecord"] = {"hipEventRecord", CONV_EVENT}; - cuda2hipRename["cudaEventElapsedTime"] = {"hipEventElapsedTime", CONV_EVENT}; - cuda2hipRename["cudaEventSynchronize"] = {"hipEventSynchronize", CONV_EVENT}; + cuda2hipRename["cudaEventElapsedTime"] = {"hipEventElapsedTime", + CONV_EVENT}; + cuda2hipRename["cudaEventSynchronize"] = {"hipEventSynchronize", + CONV_EVENT}; // Streams cuda2hipRename["cudaStream_t"] = {"hipStream_t", CONV_STREAM}; cuda2hipRename["cudaStreamCreate"] = {"hipStreamCreate", CONV_STREAM}; - cuda2hipRename["cudaStreamCreateWithFlags"] = {"hipStreamCreateWithFlags", CONV_STREAM}; + cuda2hipRename["cudaStreamCreateWithFlags"] = {"hipStreamCreateWithFlags", + CONV_STREAM}; cuda2hipRename["cudaStreamDestroy"] = {"hipStreamDestroy", CONV_STREAM}; cuda2hipRename["cudaStreamWaitEvent"] = {"hipStreamWaitEven", CONV_STREAM}; - cuda2hipRename["cudaStreamSynchronize"] = {"hipStreamSynchronize", CONV_STREAM}; + cuda2hipRename["cudaStreamSynchronize"] = {"hipStreamSynchronize", + CONV_STREAM}; cuda2hipRename["cudaStreamDefault"] = {"hipStreamDefault", CONV_STREAM}; - cuda2hipRename["cudaStreamNonBlocking"] = {"hipStreamNonBlocking", CONV_STREAM}; + cuda2hipRename["cudaStreamNonBlocking"] = {"hipStreamNonBlocking", + CONV_STREAM}; // Other synchronization - cuda2hipRename["cudaDeviceSynchronize"] = {"hipDeviceSynchronize", CONV_DEV}; - cuda2hipRename["cudaThreadSynchronize"] = - {"hipDeviceSynchronize", CONV_DEV}; // translate deprecated cudaThreadSynchronize + cuda2hipRename["cudaDeviceSynchronize"] = {"hipDeviceSynchronize", + CONV_DEV}; + cuda2hipRename["cudaThreadSynchronize"] = { + "hipDeviceSynchronize", + CONV_DEV}; // translate deprecated cudaThreadSynchronize cuda2hipRename["cudaDeviceReset"] = {"hipDeviceReset", CONV_DEV}; - cuda2hipRename["cudaThreadExit"] = - {"hipDeviceReset", CONV_DEV}; // translate deprecated cudaThreadExit + cuda2hipRename["cudaThreadExit"] = { + "hipDeviceReset", CONV_DEV}; // translate deprecated cudaThreadExit cuda2hipRename["cudaSetDevice"] = {"hipSetDevice", CONV_DEV}; cuda2hipRename["cudaGetDevice"] = {"hipGetDevice", CONV_DEV}; // Attribute cuda2hipRename["bcudaDeviceAttr"] = {"hipDeviceAttribute_t", CONV_DEV}; - cuda2hipRename["bcudaDeviceGetAttribute"] = {"hipDeviceGetAttribute", CONV_DEV}; - + cuda2hipRename["bcudaDeviceGetAttribute"] = {"hipDeviceGetAttribute", + CONV_DEV}; + // Device cuda2hipRename["cudaDeviceProp"] = {"hipDeviceProp_t", CONV_DEV}; - cuda2hipRename["cudaGetDeviceProperties"] = {"hipDeviceGetProperties", CONV_DEV}; + cuda2hipRename["cudaGetDeviceProperties"] = {"hipDeviceGetProperties", + CONV_DEV}; // Cache config - cuda2hipRename["cudaDeviceSetCacheConfig"] = {"hipDeviceSetCacheConfig", CONV_DEV}; - cuda2hipRename["cudaThreadSetCacheConfig"] = - {"hipDeviceSetCacheConfig", CONV_DEV}; // translate deprecated - cuda2hipRename["cudaDeviceGetCacheConfig"] = {"hipDeviceGetCacheConfig", CONV_DEV}; - cuda2hipRename["cudaThreadGetCacheConfig"] = - {"hipDeviceGetCacheConfig", CONV_DEV}; // translate deprecated + cuda2hipRename["cudaDeviceSetCacheConfig"] = {"hipDeviceSetCacheConfig", + CONV_DEV}; + cuda2hipRename["cudaThreadSetCacheConfig"] = { + "hipDeviceSetCacheConfig", CONV_DEV}; // translate deprecated + cuda2hipRename["cudaDeviceGetCacheConfig"] = {"hipDeviceGetCacheConfig", + CONV_DEV}; + cuda2hipRename["cudaThreadGetCacheConfig"] = { + "hipDeviceGetCacheConfig", CONV_DEV}; // translate deprecated cuda2hipRename["cudaFuncCache"] = {"hipFuncCache", CONV_DEV}; - cuda2hipRename["cudaFuncCachePreferNone"] = {"hipFuncCachePreferNone", CONV_DEV}; - cuda2hipRename["cudaFuncCachePreferShared"] = {"hipFuncCachePreferShared", CONV_DEV}; - cuda2hipRename["cudaFuncCachePreferL1"] = {"hipFuncCachePreferL1", CONV_DEV}; - cuda2hipRename["cudaFuncCachePreferEqual"] = {"hipFuncCachePreferEqual", CONV_DEV}; + cuda2hipRename["cudaFuncCachePreferNone"] = {"hipFuncCachePreferNone", + CONV_DEV}; + cuda2hipRename["cudaFuncCachePreferShared"] = {"hipFuncCachePreferShared", + CONV_DEV}; + cuda2hipRename["cudaFuncCachePreferL1"] = {"hipFuncCachePreferL1", + CONV_DEV}; + cuda2hipRename["cudaFuncCachePreferEqual"] = {"hipFuncCachePreferEqual", + CONV_DEV}; // function - cuda2hipRename["cudaFuncSetCacheConfig"] = {"hipFuncSetCacheConfig", CONV_DEV}; + cuda2hipRename["cudaFuncSetCacheConfig"] = {"hipFuncSetCacheConfig", + CONV_DEV}; cuda2hipRename["cudaDriverGetVersion"] = {"hipDriverGetVersion", CONV_DEV}; -// cuda2hipRename["cudaRuntimeGetVersion"] = {"hipRuntimeGetVersion", CONV_DEV}; + // cuda2hipRename["cudaRuntimeGetVersion"] = {"hipRuntimeGetVersion", + // CONV_DEV}; // Peer2Peer - cuda2hipRename["cudaDeviceCanAccessPeer"] = {"hipDeviceCanAccessPeer", CONV_DEV}; - cuda2hipRename["cudaDeviceDisablePeerAccess"] = - {"hipDeviceDisablePeerAccess", CONV_DEV}; - cuda2hipRename["cudaDeviceEnablePeerAccess"] = {"hipDeviceEnablePeerAccess", CONV_DEV}; + cuda2hipRename["cudaDeviceCanAccessPeer"] = {"hipDeviceCanAccessPeer", + CONV_DEV}; + cuda2hipRename["cudaDeviceDisablePeerAccess"] = { + "hipDeviceDisablePeerAccess", CONV_DEV}; + cuda2hipRename["cudaDeviceEnablePeerAccess"] = {"hipDeviceEnablePeerAccess", + CONV_DEV}; cuda2hipRename["cudaMemcpyPeerAsync"] = {"hipMemcpyPeerAsync", CONV_MEM}; cuda2hipRename["cudaMemcpyPeer"] = {"hipMemcpyPeer", CONV_MEM}; // Shared mem: - cuda2hipRename["cudaDeviceSetSharedMemConfig"] = - {"hipDeviceSetSharedMemConfig", CONV_DEV}; - cuda2hipRename["cudaThreadSetSharedMemConfig"] = - {"hipDeviceSetSharedMemConfig", CONV_DEV}; // translate deprecated - cuda2hipRename["cudaDeviceGetSharedMemConfig"] = - {"hipDeviceGetSharedMemConfig", CONV_DEV}; - cuda2hipRename["cudaThreadGetSharedMemConfig"] = - {"hipDeviceGetSharedMemConfig", CONV_DEV}; // translate deprecated + cuda2hipRename["cudaDeviceSetSharedMemConfig"] = { + "hipDeviceSetSharedMemConfig", CONV_DEV}; + cuda2hipRename["cudaThreadSetSharedMemConfig"] = { + "hipDeviceSetSharedMemConfig", CONV_DEV}; // translate deprecated + cuda2hipRename["cudaDeviceGetSharedMemConfig"] = { + "hipDeviceGetSharedMemConfig", CONV_DEV}; + cuda2hipRename["cudaThreadGetSharedMemConfig"] = { + "hipDeviceGetSharedMemConfig", CONV_DEV}; // translate deprecated cuda2hipRename["cudaSharedMemConfig"] = {"hipSharedMemConfig", CONV_DEV}; - cuda2hipRename["cudaSharedMemBankSizeDefault"] = - {"hipSharedMemBankSizeDefault", CONV_DEV}; - cuda2hipRename["cudaSharedMemBankSizeFourByte"] = - {"hipSharedMemBankSizeFourByte", CONV_DEV}; - cuda2hipRename["cudaSharedMemBankSizeEightByte"] = - {"hipSharedMemBankSizeEightByte", CONV_DEV}; + cuda2hipRename["cudaSharedMemBankSizeDefault"] = { + "hipSharedMemBankSizeDefault", CONV_DEV}; + cuda2hipRename["cudaSharedMemBankSizeFourByte"] = { + "hipSharedMemBankSizeFourByte", CONV_DEV}; + cuda2hipRename["cudaSharedMemBankSizeEightByte"] = { + "hipSharedMemBankSizeEightByte", CONV_DEV}; cuda2hipRename["cudaGetDeviceCount"] = {"hipGetDeviceCount", CONV_DEV}; @@ -245,21 +279,24 @@ struct cuda2hipMap { cuda2hipRename["cudaProfilerStart"] = {"hipProfilerStart", CONV_OTHER}; cuda2hipRename["cudaProfilerStop"] = {"hipProfilerStop", CONV_OTHER}; - cuda2hipRename["cudaChannelFormatDesc"] = {"hipChannelFormatDesc", CONV_TEX}; + cuda2hipRename["cudaChannelFormatDesc"] = {"hipChannelFormatDesc", + CONV_TEX}; cuda2hipRename["cudaFilterModePoint"] = {"hipFilterModePoint", CONV_TEX}; - cuda2hipRename["cudaReadModeElementType"] = {"hipReadModeElementType", CONV_TEX}; + cuda2hipRename["cudaReadModeElementType"] = {"hipReadModeElementType", + CONV_TEX}; - cuda2hipRename["cudaCreateChannelDesc"] = {"hipCreateChannelDesc", CONV_TEX}; + cuda2hipRename["cudaCreateChannelDesc"] = {"hipCreateChannelDesc", + CONV_TEX}; cuda2hipRename["cudaBindTexture"] = {"hipBindTexture", CONV_TEX}; cuda2hipRename["cudaUnbindTexture"] = {"hipUnbindTexture", CONV_TEX}; } - + struct HipNames { StringRef hipName; ConvTypes countType; }; - - SmallDenseMap cuda2hipRename; + + SmallDenseMap cuda2hipRename; }; StringRef unquoteStr(StringRef s) { @@ -268,14 +305,18 @@ StringRef unquoteStr(StringRef s) { return s; } -static void processString(StringRef s, struct cuda2hipMap &map, Replacements *Replace, - SourceManager &SM, SourceLocation start) { +static void processString(StringRef s, const cuda2hipMap &map, + Replacements *Replace, SourceManager &SM, + SourceLocation start, + int64_t countReps[ConvTypes::CONV_LAST]) { size_t begin = 0; while ((begin = s.find("cuda", begin)) != StringRef::npos) { const size_t end = s.find_first_of(" ", begin + 4); StringRef name = s.slice(begin, end); - StringRef repName = map.cuda2hipRename[name].hipName; - if (!repName.empty()) { + const auto found = map.cuda2hipRename.find(name); + if (found != map.cuda2hipRename.end()) { + countReps[CONV_LITERAL]++; + StringRef repName = found->second.hipName; SourceLocation sl = start.getLocWithOffset(begin + 1); Replacement Rep(SM, sl, name.size(), repName); Replace->insert(Rep); @@ -310,8 +351,10 @@ struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { const clang::Module *imported) override { if (_sm->isWrittenInMainFile(hash_loc)) { if (is_angled) { - if (N.cuda2hipRename.count(file_name)) { - StringRef repName = N.cuda2hipRename[file_name].hipName; + const auto found = N.cuda2hipRename.find(file_name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; DEBUG(dbgs() << "Include file found: " << file_name << "\n" << "SourceLocation:" << filename_range.getBegin().printToString(*_sm) << "\n" @@ -336,8 +379,10 @@ struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { for (auto T : MD->getMacroInfo()->tokens()) { if (T.isAnyIdentifier()) { StringRef name = T.getIdentifierInfo()->getName(); - if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name].hipName; + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; SourceLocation sl = T.getLocation(); DEBUG(dbgs() << "Identifier " << name << " found in definition of macro " @@ -380,12 +425,15 @@ struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { for (auto tok : toks) { if (tok.isAnyIdentifier()) { StringRef name = tok.getIdentifierInfo()->getName(); - if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name].hipName; - DEBUG(dbgs() << "Identifier " << name - << " found as an actual argument in expansion of macro " - << macroName << "\n" - << "will be replaced with: " << repName << "\n"); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + DEBUG(dbgs() + << "Identifier " << name + << " found as an actual argument in expansion of macro " + << macroName << "\n" + << "will be replaced with: " << repName << "\n"); SourceLocation sl = tok.getLocation(); Replacement Rep(*_sm, sl, name.size(), repName); Replace->insert(Rep); @@ -393,7 +441,8 @@ struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { } if (tok.is(tok::string_literal)) { StringRef s(tok.getLiteralData(), tok.getLength()); - processString(unquoteStr(s), N, Replace, *_sm, tok.getLocation()); + processString(unquoteStr(s), N, Replace, *_sm, tok.getLocation(), + countReps); } } } @@ -406,6 +455,8 @@ struct HipifyPPCallbacks : public PPCallbacks, public SourceFileCallbacks { void setSourceManager(SourceManager *sm) { _sm = sm; } void setPreprocessor(Preprocessor *pp) { _pp = pp; } + int64_t countReps[ConvTypes::CONV_LAST] = {0}; + private: SourceManager *_sm; Preprocessor *_pp; @@ -462,8 +513,10 @@ public: Result.Nodes.getNodeAs("cudaCall")) { const FunctionDecl *funcDcl = call->getDirectCallee(); StringRef name = funcDcl->getDeclName().getAsString(); - if (N.cuda2hipRename.count(name)) { - StringRef repName = N.cuda2hipRename[name].hipName; + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; SourceLocation sl = call->getLocStart(); Replacement Rep(*SM, SM->isMacroArgExpansion(sl) ? SM->getImmediateSpellingLoc(sl) @@ -498,7 +551,8 @@ public: OS << "hipLaunchKernel(HIP_KERNEL_NAME(" << calleeName << "),"; const CallExpr *config = launchKernel->getConfig(); - DEBUG(dbgs() << "Kernel config arguments:" << "\n"); + DEBUG(dbgs() << "Kernel config arguments:" + << "\n"); for (unsigned argno = 0; argno < config->getNumArgs(); argno++) { const Expr *arg = config->getArg(argno); if (!isa(arg)) { @@ -512,7 +566,8 @@ public: StringRef outs(SM->getCharacterData(sl), SM->getCharacterData(stop) - SM->getCharacterData(sl)); DEBUG(dbgs() << "args[ " << argno << "]" << outs << " <" - << pvd->getType().getAsString() << ">" << "\n"); + << pvd->getType().getAsString() << ">" + << "\n"); if (pvd->getType().getAsString().compare("dim3") == 0) OS << " dim3(" << outs << "),"; else @@ -540,6 +595,7 @@ public: SM->getCharacterData(launchKernel->getLocStart()); Replacement Rep(*SM, launchKernel->getLocStart(), length, OS.str()); Replace->insert(Rep); + countReps[ConvTypes::CONV_KERN]++; } if (const FunctionTemplateDecl *templateDecl = @@ -561,10 +617,14 @@ public: memberName = memberName.slice(pos, memberName.size()); SmallString<128> tmpData; name = Twine(name + "." + memberName).toStringRef(tmpData); - StringRef repName = N.cuda2hipRename[name].hipName; - SourceLocation sl = threadIdx->getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + SourceLocation sl = threadIdx->getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } } } } @@ -572,20 +632,28 @@ public: if (const DeclRefExpr *cudaEnumConstantRef = Result.Nodes.getNodeAs("cudaEnumConstantRef")) { StringRef name = cudaEnumConstantRef->getDecl()->getNameAsString(); - StringRef repName = N.cuda2hipRename[name].hipName; - SourceLocation sl = cudaEnumConstantRef->getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + SourceLocation sl = cudaEnumConstantRef->getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } } if (const VarDecl *cudaEnumConstantDecl = Result.Nodes.getNodeAs("cudaEnumConstantDecl")) { StringRef name = cudaEnumConstantDecl->getType()->getAsTagDecl()->getNameAsString(); - StringRef repName = N.cuda2hipRename[name].hipName; - SourceLocation sl = cudaEnumConstantDecl->getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + SourceLocation sl = cudaEnumConstantDecl->getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } } if (const VarDecl *cudaStructVar = @@ -594,11 +662,15 @@ public: ->getAsStructureType() ->getDecl() ->getNameAsString(); - StringRef repName = N.cuda2hipRename[name].hipName; - TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + TypeLoc TL = cudaStructVar->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } } if (const VarDecl *cudaStructVarPtr = @@ -606,11 +678,15 @@ public: const Type *t = cudaStructVarPtr->getType().getTypePtrOrNull(); if (t) { StringRef name = t->getPointeeCXXRecordDecl()->getName(); - StringRef repName = N.cuda2hipRename[name].hipName; - TypeLoc TL = cudaStructVarPtr->getTypeSourceInfo()->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + TypeLoc TL = cudaStructVarPtr->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } } } @@ -622,11 +698,15 @@ public: if (t->isStructureOrClassType()) { name = t->getAsCXXRecordDecl()->getName(); } - StringRef repName = N.cuda2hipRename[name].hipName; - TypeLoc TL = cudaParamDecl->getTypeSourceInfo()->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + TypeLoc TL = cudaParamDecl->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } } if (const ParmVarDecl *cudaParamDeclPtr = @@ -638,11 +718,15 @@ public: StringRef name = t->isStructureOrClassType() ? t->getAsCXXRecordDecl()->getName() : StringRef(QT.getAsString()); - StringRef repName = N.cuda2hipRename[name].hipName; - TypeLoc TL = cudaParamDeclPtr->getTypeSourceInfo()->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + TypeLoc TL = cudaParamDeclPtr->getTypeSourceInfo()->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } } } @@ -650,7 +734,8 @@ public: Result.Nodes.getNodeAs("stringLiteral")) { if (stringLiteral->getCharByteWidth() == 1) { StringRef s = stringLiteral->getString(); - processString(s, N, Replace, *SM, stringLiteral->getLocStart()); + processString(s, N, Replace, *SM, stringLiteral->getLocStart(), + countReps); } } @@ -661,14 +746,20 @@ public: QualType QT = typeInfo->getType().getUnqualifiedType(); const Type *type = QT.getTypePtr(); StringRef name = type->getAsCXXRecordDecl()->getName(); - StringRef repName = N.cuda2hipRename[name].hipName; - TypeLoc TL = typeInfo->getTypeLoc(); - SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); - Replacement Rep(*SM, sl, name.size(), repName); - Replace->insert(Rep); + const auto found = N.cuda2hipRename.find(name); + if (found != N.cuda2hipRename.end()) { + countReps[found->second.countType]++; + StringRef repName = found->second.hipName; + TypeLoc TL = typeInfo->getTypeLoc(); + SourceLocation sl = TL.getUnqualifiedLoc().getLocStart(); + Replacement Rep(*SM, sl, name.size(), repName); + Replace->insert(Rep); + } } } + int64_t countReps[ConvTypes::CONV_LAST] = {0}; + private: Replacements *Replace; ast_matchers::MatchFinder *owner; @@ -694,13 +785,12 @@ static cl::opt static cl::opt NoOutput("no-output", - cl::desc("don't write any translated output to stdout"), - cl::value_desc("no-output"), cl::cat(ToolTemplateCategory)); + cl::desc("don't write any translated output to stdout"), + cl::value_desc("no-output"), cl::cat(ToolTemplateCategory)); static cl::opt - PrintStats("print-stats", - cl::desc("print the command-line, like a header"), - cl::value_desc("print-stats"), cl::cat(ToolTemplateCategory)); - + PrintStats("print-stats", cl::desc("print the command-line, like a header"), + cl::value_desc("print-stats"), cl::cat(ToolTemplateCategory)); + int main(int argc, const char **argv) { llvm::sys::PrintStackTraceOnErrorSignal(); @@ -788,7 +878,7 @@ int main(int argc, const char **argv) { std::vector compilationStages; compilationStages.push_back("--cuda-host-only"); - compilationStages.push_back("--cuda-device-only"); + //compilationStages.push_back("--cuda-device-only"); for (auto Stage : compilationStages) { Tool.appendArgumentsAdjuster( @@ -797,7 +887,7 @@ int main(int argc, const char **argv) { #if defined(HIPIFY_CLANG_RES) Tool.appendArgumentsAdjuster( getInsertArgumentAdjuster("-resource-dir=" HIPIFY_CLANG_RES)); -#endif // defined(HIPIFY_CLANG_HEADERS) +#endif Tool.appendArgumentsAdjuster(getClangSyntaxOnlyAdjuster()); Result = Tool.run(action.get()); @@ -831,5 +921,17 @@ int main(int argc, const char **argv) { rename(dst.c_str(), dst.substr(0, pos).c_str()); } } + if (PrintStats) { + int64_t sum = 0; + for (int i = 0; i < ConvTypes::CONV_LAST; i++) { + sum += Callback.countReps[i] + PPCallbacks.countReps[i]; + } + llvm::outs() << "info: converted " << sum << " CUDA->HIP refs ( "; + for (int i = 0; i < ConvTypes::CONV_LAST; i++) { + llvm::outs() << counterNames[i] << ':' + << Callback.countReps[i] + PPCallbacks.countReps[i] << ' '; + } + llvm::outs() << ") in \'" << fileSources[0] << "\'\n"; + } return Result; } diff --git a/hipamd/test/axpy.cu b/hipamd/test/axpy.cu index 9e83ccb7e6..92f61267a4 100644 --- a/hipamd/test/axpy.cu +++ b/hipamd/test/axpy.cu @@ -23,7 +23,7 @@ int main(int argc, char* argv[]) { cudaMemcpy(device_x, host_x, kDataLen * sizeof(float), cudaMemcpyHostToDevice); // Launch the kernel. - // CHECK: hipLaunchKernel(HIP_KERNEL_NAME(axpy), dim3(1), dim3(kDataLen), 0, 0, a, device_x, device_y); + // CHECK: hipLaunchKernel(HIP_KERNEL_NAME(axpy), dim3(1), dim3(kDataLen), 0, 0, a, device_x, device_y); axpy<<<1, kDataLen>>>(a, device_x, device_y); // Copy output data to host. From 666a887a1e4c39464a1fdc0b53b9668e366f16b5 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Sat, 26 Mar 2016 16:01:49 +0300 Subject: [PATCH 37/56] removed FileCheck dependency & significantly improved test coverage --- hipamd/README.md | 5 ++--- hipamd/test/CMakeLists.txt | 2 +- hipamd/test/axpy.cu | 11 ++++++++--- hipamd/test/lit.cfg | 7 ------- 4 files changed, 11 insertions(+), 14 deletions(-) diff --git a/hipamd/README.md b/hipamd/README.md index 743a1a63b2..0b37244def 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -13,7 +13,7 @@ git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git ll echo "add_subdirectory(hipify)" >> llvm/tools/clang/tools/extra/CMakeLists.txt mkdir llvm_build && cd llvm_build -cmake -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm +cmake -DLLVM_TARGETS_TO_BUILD="X86;NVPTX" ../llvm make ``` @@ -25,7 +25,7 @@ git clone http://llvm.org/git/llvm.git llvm git clone http://llvm.org/git/clang.git llvm/tools/clang mkdir llvm_build && cd llvm_build -cmake -DCMAKE_INSTALL_PREFIX="LLVM_INSTALL_PATH" -DLLVM_INSTALL_UTILS=ON -DLLVM_TARGETS_TO_BUILD="X86;NVPTX;AMDGPU" ../llvm +cmake -DCMAKE_INSTALL_PREFIX="LLVM_INSTALL_PATH" -DLLVM_TARGETS_TO_BUILD="X86;NVPTX" ../llvm make && make install git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git path_to_hipify_src @@ -37,7 +37,6 @@ make # How to run tests (for *standalone* tool only) - install Python and add python-setuptools - install lit python script -- make sure that FileCheck util is installed to **LLVM_INSTALL_PATH/bin/FileCheck** - run tests from path_to_hipify_src/build ``` sudo apt-get install python python-setuptools diff --git a/hipamd/test/CMakeLists.txt b/hipamd/test/CMakeLists.txt index 5a0250381d..ba472ad2ee 100644 --- a/hipamd/test/CMakeLists.txt +++ b/hipamd/test/CMakeLists.txt @@ -16,7 +16,7 @@ configure_file( add_lit_testsuite(check-hipify "Running HIPify regression tests" ${CMAKE_CURRENT_SOURCE_DIR} PARAMS site_config=${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg - DEPENDS hipify FileCheck lit + DEPENDS hipify lit ) add_custom_target(check) diff --git a/hipamd/test/axpy.cu b/hipamd/test/axpy.cu index 92f61267a4..8472e60209 100644 --- a/hipamd/test/axpy.cu +++ b/hipamd/test/axpy.cu @@ -1,10 +1,9 @@ // RUN: hipify "%s" -o=%t -- -// RUN: FileCheck %s -input-file=%t --match-full-lines #include __global__ void axpy(float a, float* x, float* y) { - // CHECK: y[hipThreadIdx_x] = a * x[hipThreadIdx_x]; + // RUN: sh -c "test `grep -c -F 'y[hipThreadIdx_x] = a * x[hipThreadIdx_x];' %t` -eq 2" y[threadIdx.x] = a * x[threadIdx.x]; } @@ -18,16 +17,21 @@ int main(int argc, char* argv[]) { // Copy input data to device. float* device_x; float* device_y; + // RUN: sh -c "test `grep -c -F 'hipMalloc(&device_x, kDataLen * sizeof(float));' %t` -eq 2" cudaMalloc(&device_x, kDataLen * sizeof(float)); + // RUN: sh -c "test `grep -c -F 'hipMalloc(&device_y, kDataLen * sizeof(float));' %t` -eq 2" cudaMalloc(&device_y, kDataLen * sizeof(float)); + // RUN: sh -c "test `grep -c -F 'hipMemcpy(device_x, host_x, kDataLen * sizeof(float), hipMemcpyHostToDevice);' %t` -eq 2" cudaMemcpy(device_x, host_x, kDataLen * sizeof(float), cudaMemcpyHostToDevice); // Launch the kernel. - // CHECK: hipLaunchKernel(HIP_KERNEL_NAME(axpy), dim3(1), dim3(kDataLen), 0, 0, a, device_x, device_y); + // RUN: sh -c "test `grep -c -F 'hipLaunchKernel(HIP_KERNEL_NAME(axpy), dim3(1), dim3(kDataLen), 0, 0, a, device_x, device_y);' %t` -eq 2" axpy<<<1, kDataLen>>>(a, device_x, device_y); // Copy output data to host. + // RUN: sh -c "test `grep -c -F 'hipDeviceSynchronize();' %t` -eq 2" cudaDeviceSynchronize(); + // RUN: sh -c "test `grep -c -F 'hipMemcpy(host_y, device_y, kDataLen * sizeof(float), hipMemcpyDeviceToHost);' %t` -eq 2" cudaMemcpy(host_y, device_y, kDataLen * sizeof(float), cudaMemcpyDeviceToHost); // Print the results. @@ -35,6 +39,7 @@ int main(int argc, char* argv[]) { std::cout << "y[" << i << "] = " << host_y[i] << "\n"; } + // RUN: sh -c "test `grep -c -F 'hipDeviceReset();' %t` -eq 2" cudaDeviceReset(); return 0; } diff --git a/hipamd/test/lit.cfg b/hipamd/test/lit.cfg index d9606b48fc..5c070ae053 100644 --- a/hipamd/test/lit.cfg +++ b/hipamd/test/lit.cfg @@ -44,12 +44,5 @@ if obj_root is not None: path = os.path.pathsep.join((llvm_tools_dir, config.environment['PATH'])) config.environment['PATH'] = path -tool_name = "FileCheck" -tool_path = lit.util.which(tool_name, llvm_tools_dir) -if not tool_path: - # Warn, but still provide a substitution. - lit_config.note('Did not find ' + tool_name + ' in ' + llvm_tools_dir) - tool_path = llvm_tools_dir + '/' + tool_name -config.substitutions.append((tool_name, tool_path)) config.substitutions.append(("hipify", obj_root+"/hipify")) From d854d3650cb80b82a81e140fe0d7a7898a6670cc Mon Sep 17 00:00:00 2001 From: dfukalov Date: Tue, 5 Apr 2016 00:10:21 +0300 Subject: [PATCH 38/56] initial cmake add --- hipamd/CMakeLists.txt | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 6b25a21394..b3daa69aa6 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -5,6 +5,9 @@ if(NOT CMAKE_BUILD_TYPE) set(CMAKE_BUILD_TYPE "Release") endif() +set(HIPIFY_STANDLONE 1) +add_subdirectory(clang-hipify) + if(NOT DEFINED HCC_HOME) if(NOT DEFINED ENV{HCC_HOME}) set(HCC_HOME "/opt/hcc" CACHE PATH "Path to which HCC has been installed") @@ -55,14 +58,7 @@ set(CMAKE_CXX_FLAGS " -hc -I${HCC_HOME}/include -I${HSA_PATH}/include -stdlib=li set(CMAKE_C_FLAGS " -hc -I${HCC_HOME}/include -I${HSA_PATH}/include -stdlib=libc++ ") set(SOURCE_FILES src/device_util.cpp -src/hip_hcc.cpp -src/hip_device.cpp -src/hip_error.cpp -src/hip_event.cpp -src/hip_memory.cpp -src/hip_peer.cpp -src/hip_stream.cpp -src/staging_buffer.cpp) +) if(NOT DEFINED ENV{HIP_USE_SHARED_LIBRARY}) set(HIP_USE_SHARED_LIBRARY 0) From f1e64fe2b412ac0b1af2d1d10d00c37fbb3f8b73 Mon Sep 17 00:00:00 2001 From: dfukalov Date: Wed, 6 Apr 2016 20:44:19 +0300 Subject: [PATCH 39/56] moved clang-hipify tests to common folder "tests", updated cmake files to use downloadable clang+llvm binary package --- hipamd/CMakeLists.txt | 1 - hipamd/clang-hipify/CMakeLists.txt | 76 +++++++++++-------- hipamd/clang-hipify/test/CMakeLists.txt | 27 ------- .../test => tests/clang-hipify}/axpy.cu | 0 .../test => tests/clang-hipify}/lit.cfg | 2 +- .../clang-hipify}/lit.site.cfg.in | 0 6 files changed, 45 insertions(+), 61 deletions(-) delete mode 100644 hipamd/clang-hipify/test/CMakeLists.txt rename hipamd/{clang-hipify/test => tests/clang-hipify}/axpy.cu (100%) rename hipamd/{clang-hipify/test => tests/clang-hipify}/lit.cfg (95%) rename hipamd/{clang-hipify/test => tests/clang-hipify}/lit.site.cfg.in (100%) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index b3daa69aa6..5346ea7c69 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -5,7 +5,6 @@ if(NOT CMAKE_BUILD_TYPE) set(CMAKE_BUILD_TYPE "Release") endif() -set(HIPIFY_STANDLONE 1) add_subdirectory(clang-hipify) if(NOT DEFINED HCC_HOME) diff --git a/hipamd/clang-hipify/CMakeLists.txt b/hipamd/clang-hipify/CMakeLists.txt index 18e8e7df4d..574677aa7e 100644 --- a/hipamd/clang-hipify/CMakeLists.txt +++ b/hipamd/clang-hipify/CMakeLists.txt @@ -1,32 +1,22 @@ -if(${HIPIFY_STANDLONE}) - cmake_minimum_required(VERSION 2.8.8) +cmake_minimum_required(VERSION 2.8.8) - project(hipify) +project(hipify-clang) - find_package(LLVM REQUIRED PATHS ${LLVM_DIR} NO_DEFAULT_PATH) +find_package(LLVM 3.8 REQUIRED PATHS ${LLVM_DIR} NO_DEFAULT_PATH) - list(APPEND CMAKE_MODULE_PATH ${LLVM_CMAKE_DIR}) - include(AddLLVM) +list(APPEND CMAKE_MODULE_PATH ${LLVM_CMAKE_DIR}) +include(AddLLVM) - message(STATUS "Found LLVM ${LLVM_PACKAGE_VERSION}") - message(STATUS "Using LLVMConfig.cmake in: ${LLVM_DIR}") - - include_directories(${LLVM_INCLUDE_DIRS}) - link_directories(${LLVM_LIBRARY_DIRS}) - add_definitions(${LLVM_DEFINITIONS}) - add_llvm_executable(hipify src/Cuda2Hip.cpp ) - find_program(LIT_COMMAND lit) -else() - set(LLVM_LINK_COMPONENTS - Option - Support - ) - add_clang_executable(hipify src/Cuda2Hip.cpp) -endif() +message(STATUS "Found LLVM ${LLVM_PACKAGE_VERSION}") +include_directories(${LLVM_INCLUDE_DIRS}) +link_directories(${LLVM_LIBRARY_DIRS}) +add_definitions(${LLVM_DEFINITIONS}) +add_llvm_executable(hipify-clang src/Cuda2Hip.cpp ) +find_program(LIT_COMMAND lit) # Link against LLVM and CLANG tools libraries -target_link_libraries(hipify +target_link_libraries(hipify-clang clangASTMatchers clangFrontend clangTooling @@ -49,14 +39,36 @@ target_link_libraries(hipify LLVMOption LLVMCore) -if(${HIPIFY_STANDLONE}) - set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_CFLAGS}") - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS}") - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -std=c++11 -pthread -fno-rtti -fvisibility-inlines-hidden") - set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DHIPIFY_CLANG_RES=\\\"${LLVM_LIBRARY_DIRS}/clang/${LLVM_VERSION_MAJOR}.${LLVM_VERSION_MINOR}.${LLVM_VERSION_PATCH}\\\"") - add_subdirectory(test) -else() - install(TARGETS hipify - RUNTIME DESTINATION bin - COMPONENT clang-extras) +set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_CFLAGS}") +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS}") +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11 -pthread -fno-rtti -fvisibility-inlines-hidden") +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DHIPIFY_CLANG_RES=\\\"${LLVM_LIBRARY_DIRS}/clang/${LLVM_VERSION_MAJOR}.${LLVM_VERSION_MINOR}.${LLVM_VERSION_PATCH}\\\"") + +install(TARGETS hipify-clang + DESTINATION bin) + +# tests +set(Python_ADDITIONAL_VERSIONS 2.7) +include(FindPythonInterp) +if( NOT PYTHONINTERP_FOUND ) + message(FATAL_ERROR + "Unable to find Python interpreter, required for builds and testing\n\n" + "Please install Python or specify the PYTHON_EXECUTABLE CMake variable.") endif() + +set(BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR} ) + +configure_file( + ${CMAKE_SOURCE_DIR}/tests/clang-hipify/lit.site.cfg.in + ${CMAKE_CURRENT_BINARY_DIR}/tests/clang-hipify/lit.site.cfg + @ONLY) + +add_lit_testsuite(test-hipify "Running HIPify regression tests" + ${CMAKE_SOURCE_DIR}/tests/clang-hipify + PARAMS site_config=${CMAKE_CURRENT_BINARY_DIR}/tests/clang-hipify/lit.site.cfg + DEPENDS hipify-clang lit + ) + +add_custom_target(test-clang-hipify) +add_dependencies(test-clang-hipify test-hipify) +set_target_properties(test-clang-hipify PROPERTIES FOLDER "Tests") diff --git a/hipamd/clang-hipify/test/CMakeLists.txt b/hipamd/clang-hipify/test/CMakeLists.txt deleted file mode 100644 index ba472ad2ee..0000000000 --- a/hipamd/clang-hipify/test/CMakeLists.txt +++ /dev/null @@ -1,27 +0,0 @@ -set(Python_ADDITIONAL_VERSIONS 2.7) -include(FindPythonInterp) -if( NOT PYTHONINTERP_FOUND ) - message(FATAL_ERROR - "Unable to find Python interpreter, required for builds and testing\n\n" - "Please install Python or specify the PYTHON_EXECUTABLE CMake variable.") -endif() - -set(BINARY_DIR ${CMAKE_CURRENT_BINARY_DIR}/.. ) - -configure_file( - ${CMAKE_CURRENT_SOURCE_DIR}/lit.site.cfg.in - ${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg - @ONLY) - -add_lit_testsuite(check-hipify "Running HIPify regression tests" - ${CMAKE_CURRENT_SOURCE_DIR} - PARAMS site_config=${CMAKE_CURRENT_BINARY_DIR}/lit.site.cfg - DEPENDS hipify lit - ) - -add_custom_target(check) -add_dependencies(check check-hipify) -add_custom_target(test) -add_dependencies(test check-hipify) -set_target_properties(check PROPERTIES FOLDER "Tests") - diff --git a/hipamd/clang-hipify/test/axpy.cu b/hipamd/tests/clang-hipify/axpy.cu similarity index 100% rename from hipamd/clang-hipify/test/axpy.cu rename to hipamd/tests/clang-hipify/axpy.cu diff --git a/hipamd/clang-hipify/test/lit.cfg b/hipamd/tests/clang-hipify/lit.cfg similarity index 95% rename from hipamd/clang-hipify/test/lit.cfg rename to hipamd/tests/clang-hipify/lit.cfg index 5c070ae053..c57b8ec524 100644 --- a/hipamd/clang-hipify/test/lit.cfg +++ b/hipamd/tests/clang-hipify/lit.cfg @@ -44,5 +44,5 @@ if obj_root is not None: path = os.path.pathsep.join((llvm_tools_dir, config.environment['PATH'])) config.environment['PATH'] = path -config.substitutions.append(("hipify", obj_root+"/hipify")) +config.substitutions.append(("hipify", obj_root+"/hipify-clang")) diff --git a/hipamd/clang-hipify/test/lit.site.cfg.in b/hipamd/tests/clang-hipify/lit.site.cfg.in similarity index 100% rename from hipamd/clang-hipify/test/lit.site.cfg.in rename to hipamd/tests/clang-hipify/lit.site.cfg.in From 52fab0ca63f75d78b5fdee51791ad4af3a46dae4 Mon Sep 17 00:00:00 2001 From: Daniil Fukalov Date: Thu, 7 Apr 2016 00:36:27 +0300 Subject: [PATCH 40/56] added clang-hipify added option to cmake and description how to download and install clang-hipify prerequisites --- hipamd/README.md | 22 +++++++++++++++++++--- 1 file changed, 19 insertions(+), 3 deletions(-) diff --git a/hipamd/README.md b/hipamd/README.md index 810c378436..9d5cf663b0 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -15,11 +15,11 @@ New projects can be developed directly in the portable HIP C++ language and can cd HIP-privatestaging mkdir build cd build -cmake -DHSA_PATH=/path/to/hsa -DHCC_HOME=/path/to/hcc -DCMAKE_INSTALL_PREFIX=/where/to/install/hip -DCMAKE_BUILD_TYPE=Release .. +cmake -DHSA_PATH=/path/to/hsa -DHCC_HOME=/path/to/hcc -DCMAKE_INSTALL_PREFIX=/where/to/install/hip -DLLVM_DIR=/path/to/clang-llvm-3.8 -DCMAKE_BUILD_TYPE=Release .. make make install ``` -Make sure HIP_PATH is pointed to `/where/to/install/hip` and PATH includes `$HIP_PATH/bin`. This requirement is optional, but required to run any HIP test infrastructure. +Make sure HIP_PATH is pointed to `/where/to/install/hip` and PATH includes `$HIP_PATH/bin`. This requirement is optional, but required to run any HIP test infrastructure. The path `/path/to/clang-llvm-3.8` should be specified for [clang-hipify](README.md#clang-hipify) utility build. ## More Info: - [HIP FAQ](docs/markdown/hip_faq.md) @@ -42,7 +42,23 @@ HIP code can be developed either on AMD HSA or Boltzmann platform using hcc comp * By default HIP looks for hcc in /opt/hcc (can be overridden by setting HCC_HOME environment variable) * By default HIP looks for HSA in /opt/hsa (can be overridden by setting HSA_PATH environment variable) * Ensure that ROCR runtime is installed and added to LD_LIBRARY_PATH - + +#####clang-hipify +To build and run clang based hipify utiliy a set of CUDA headers and clang+llvm 3.8 binary package are required: +- download and install CUDA minimal prerequisites: + 1. Download "deb(network)" variant of target installer from https://developer.nvidia.com/cuda-downloads. E.g. at the moment the link is http://developer.download.nvidia.com/compute/cuda/repos/ubuntu1404/x86_64/cuda-repo-ubuntu1404_7.5-18_amd64.deb + 2. install clang prerequisites with the following commands: +``` +wget http://developer.download.nvidia.com/compute/cuda/repos/ubuntu1404/x86_64/cuda-repo-ubuntu1404_7.5-18_amd64.deb +sudo dpkg -i cuda-repo-ubuntu1404_7.5-18_amd64.deb +sudo apt-get update && sudo apt-get install cuda-minimal-build-7-5 cuda-curand-dev-7-5 +``` +- download and unpack clang+llvm 3.8 binary package: +``` +wget http://llvm.org/releases/3.8.0/clang+llvm-3.8.0-x86_64-linux-gnu-ubuntu-14.04.tar.xz +tar xvfJ clang+llvm-3.8.0-x86_64-linux-gnu-ubuntu-14.04.tar.xz -C /path/to/clang-llvm-3.8 +``` + #### NVIDIA (nvcc) * Install CUDA SDK from manufacturer website * By default HIP looks for CUDA SDK in /usr/local/cuda (can be overriden by setting CUDA_PATH env variable) From 06dfaa4cf4f699eb755d8e7fc7418b06f4e6de3c Mon Sep 17 00:00:00 2001 From: Daniil Fukalov Date: Thu, 7 Apr 2016 00:37:20 +0300 Subject: [PATCH 41/56] Delete README.md --- hipamd/clang-hipify/README.md | 52 ----------------------------------- 1 file changed, 52 deletions(-) delete mode 100644 hipamd/clang-hipify/README.md diff --git a/hipamd/clang-hipify/README.md b/hipamd/clang-hipify/README.md deleted file mode 100644 index 0b37244def..0000000000 --- a/hipamd/clang-hipify/README.md +++ /dev/null @@ -1,52 +0,0 @@ -# HIPIFY -The CLANG-based HIPIFY tool - translates CUDA to [HIP](https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP/blob/master/README.md) - -# How to Build tool *in llvm source tree* -- get LLVM, CLANG and clang-tools-extra sources -- put hipify folder into llvm/tools/clang/tools/extra, add it to llvm/tools/clang/tools/extra/CMakeLists.txt -- run cmake and build tool -``` -git clone http://llvm.org/git/llvm.git llvm -git clone http://llvm.org/git/clang.git llvm/tools/clang -git clone http://llvm.org/git/clang-tools-extra.git llvm/tools/clang/tools/extra -git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git llvm/tools/clang/tools/extra/hipify -echo "add_subdirectory(hipify)" >> llvm/tools/clang/tools/extra/CMakeLists.txt - -mkdir llvm_build && cd llvm_build -cmake -DLLVM_TARGETS_TO_BUILD="X86;NVPTX" ../llvm -make -``` - -# How to Build *standalone* tool -- Get LLVM and CLANG sources, build them and install to a **LLVM_INSTALL_PATH** folder -- mkdir for hipify, run cmake there and build the tool: -``` -git clone http://llvm.org/git/llvm.git llvm -git clone http://llvm.org/git/clang.git llvm/tools/clang - -mkdir llvm_build && cd llvm_build -cmake -DCMAKE_INSTALL_PREFIX="LLVM_INSTALL_PATH" -DLLVM_TARGETS_TO_BUILD="X86;NVPTX" ../llvm -make && make install - -git clone https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP-hipify.git path_to_hipify_src -mkdir path_to_hipify_src/build && cd path_to_hipify_src/build -cmake -DLLVM_DIR="LLVM_INSTALL_PATH" -DHIPIFY_STANDLONE=1 .. -make -``` - -# How to run tests (for *standalone* tool only) -- install Python and add python-setuptools -- install lit python script -- run tests from path_to_hipify_src/build -``` -sudo apt-get install python python-setuptools -sudo easy_install lit -make -C path_to_hipify_src/build test -``` - -# Notes -- To run, the tool needs "cuda minimal build" package: - 1. Download target installer from https://developer.nvidia.com/cuda-downloads. Choose "deb(network)" installer type to reduce downloaded packages size (we don't need the whole set) - 2. Run `sudo dpkg -i cuda-repo-ubuntu1404_7.5-18_amd64.deb` - 3. Run `sudo apt-get update` - 4. Run `sudo apt-get install cuda-minimal-build-7-5 cuda-curand-dev-7-5` - this will install needed files, (without nvidia drivers, runtime, tools etc.) From f6678e146df1a656e45335de6f5876c69ce09a3a Mon Sep 17 00:00:00 2001 From: Daniil Fukalov Date: Thu, 7 Apr 2016 01:00:19 +0300 Subject: [PATCH 42/56] reverting accidentially removed files --- hipamd/CMakeLists.txt | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 5346ea7c69..8c078a91d8 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -57,7 +57,14 @@ set(CMAKE_CXX_FLAGS " -hc -I${HCC_HOME}/include -I${HSA_PATH}/include -stdlib=li set(CMAKE_C_FLAGS " -hc -I${HCC_HOME}/include -I${HSA_PATH}/include -stdlib=libc++ ") set(SOURCE_FILES src/device_util.cpp -) +src/hip_hcc.cpp +src/hip_device.cpp +src/hip_error.cpp +src/hip_event.cpp +src/hip_memory.cpp +src/hip_peer.cpp +src/hip_stream.cpp +src/staging_buffer.cpp) if(NOT DEFINED ENV{HIP_USE_SHARED_LIBRARY}) set(HIP_USE_SHARED_LIBRARY 0) From fb19b58840cbde9acf232aa8df726c48bc8978f4 Mon Sep 17 00:00:00 2001 From: alex-t Date: Thu, 14 Apr 2016 13:48:58 +0300 Subject: [PATCH 43/56] Fixed incorrect kernel paramlist replacement length & hipGetDeviceProperties mapping --- hipamd/clang-hipify/src/Cuda2Hip.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/hipamd/clang-hipify/src/Cuda2Hip.cpp b/hipamd/clang-hipify/src/Cuda2Hip.cpp index 65c051ec04..1e29c65010 100644 --- a/hipamd/clang-hipify/src/Cuda2Hip.cpp +++ b/hipamd/clang-hipify/src/Cuda2Hip.cpp @@ -215,7 +215,7 @@ struct cuda2hipMap { // Device cuda2hipRename["cudaDeviceProp"] = {"hipDeviceProp_t", CONV_DEV}; - cuda2hipRename["cudaGetDeviceProperties"] = {"hipDeviceGetProperties", + cuda2hipRename["cudaGetDeviceProperties"] = {"hipGetDeviceProperties", CONV_DEV}; // Cache config @@ -492,7 +492,7 @@ public: SourceLocation kernelArgListEnd(pvdLast->getLocEnd()); SourceLocation stop = clang::Lexer::getLocForEndOfToken( kernelArgListEnd, 0, *SM, DefaultLangOptions); - size_t replacementLength = + replacementLength += SM->getCharacterData(stop) - SM->getCharacterData(kernelArgListStart); initialParamList = StringRef(SM->getCharacterData(kernelArgListStart), replacementLength); From 6773a64b228c8e896032f163c7b9edc5b83af2cc Mon Sep 17 00:00:00 2001 From: bwicakso Date: Wed, 20 Apr 2016 15:51:39 -0500 Subject: [PATCH 44/56] Fix for kernel synchronization The completion future of a particular kernel is lost if there are multiple kernels in the stream. This can cause a racing condition where the signal associated with the unreferenced completion_future might get released by hcc runtime. --- hipamd/include/hcc_detail/hip_hcc.h | 6 +++++- hipamd/src/hip_hcc.cpp | 5 +++++ 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/hipamd/include/hcc_detail/hip_hcc.h b/hipamd/include/hcc_detail/hip_hcc.h index 58b58e2c99..5fa9be0fbc 100644 --- a/hipamd/include/hcc_detail/hip_hcc.h +++ b/hipamd/include/hcc_detail/hip_hcc.h @@ -440,9 +440,13 @@ public: hc::accelerator_view _av; unsigned _flags; -private: // Critical Data. THis MUST be accessed through LockedAccessor_StreamCrit_t +private: + // Critical Data. THis MUST be accessed through LockedAccessor_StreamCrit_t ihipStreamCritical_t _criticalData; + // Array of dependency completion_future. + std::vector _depFutures; + private: void enqueueBarrier(hsa_queue_t* queue, ihipSignal_t *depSignal); void waitCopy(LockedAccessor_StreamCrit_t &crit, ihipSignal_t *signal); diff --git a/hipamd/src/hip_hcc.cpp b/hipamd/src/hip_hcc.cpp index 44cccf14fa..64d529f875 100644 --- a/hipamd/src/hip_hcc.cpp +++ b/hipamd/src/hip_hcc.cpp @@ -181,6 +181,8 @@ void ihipStream_t::wait(LockedAccessor_StreamCrit_t &crit, bool assertQueueEmpty // Reset the stream to "empty" - next command will not set up an inpute dependency on any older signal. crit->_last_command_type = ihipCommandCopyH2D; crit->_last_copy_signal = NULL; + + _depFutures.clear(); } @@ -428,6 +430,9 @@ int ihipStream_t::preCopyCommand(LockedAccessor_StreamCrit_t &crit, ihipSignal_t needSync = 1; hsa_signal_t *hsaSignal = (static_cast (crit->_last_kernel_future.get_native_handle())); if (hsaSignal) { + // Keep reference to the kernel future in order to keep the + // dependent signal alive. + _depFutures.push_back(crit->_last_kernel_future); *waitSignal = * hsaSignal; } else { assert(0); // if NULL signal, and we return 1, hsa_amd_memory_copy_async will fail. Confirm this never happens. From f571c5ec7cca23d91c13222497863a9042c9aad4 Mon Sep 17 00:00:00 2001 From: Aditya Atluri Date: Mon, 25 Apr 2016 11:05:30 -0500 Subject: [PATCH 45/56] fixed hipmemset to use native ihip api --- hipamd/src/hip_memory.cpp | 49 ++++++++++++++++++++++++++++++++++++--- 1 file changed, 46 insertions(+), 3 deletions(-) diff --git a/hipamd/src/hip_memory.cpp b/hipamd/src/hip_memory.cpp index 01b24a9e13..4107be44ab 100644 --- a/hipamd/src/hip_memory.cpp +++ b/hipamd/src/hip_memory.cpp @@ -419,10 +419,53 @@ hipError_t hipMemsetAsync(void* dst, int value, size_t sizeBytes, hipStream_t s hipError_t hipMemset(void* dst, int value, size_t sizeBytes ) { - HIP_INIT_API(dst, value, sizeBytes); - + hipStream_t stream = hipStreamNull; // TODO - call an ihip memset so HIP_TRACE is correct. - return hipMemsetAsync(dst, value, sizeBytes, hipStreamNull); + HIP_INIT_API(dst, value, sizeBytes, stream); + + hipError_t e = hipSuccess; + + stream = ihipSyncAndResolveStream(stream); + + if (stream) { + stream->lockopen_preKernelCommand(); + + hc::completion_future cf ; + + if ((sizeBytes & 0x3) == 0) { + // use a faster dword-per-workitem copy: + try { + value = value & 0xff; + unsigned value32 = (value << 24) | (value << 16) | (value << 8) | (value) ; + cf = ihipMemsetKernel (stream, static_cast (dst), value32, sizeBytes/sizeof(unsigned)); + } + catch (std::exception &ex) { + e = hipErrorInvalidValue; + } + } else { + // use a slow byte-per-workitem copy: + try { + cf = ihipMemsetKernel (stream, static_cast (dst), value, sizeBytes); + } + catch (std::exception &ex) { + e = hipErrorInvalidValue; + } + } + cf.wait(); + + stream->lockclose_postKernelCommand(cf); + + + if (HIP_LAUNCH_BLOCKING) { + tprintf (DB_SYNC, "'%s' LAUNCH_BLOCKING wait for memset [stream:%p].\n", __func__, (void*)stream); + cf.wait(); + tprintf (DB_SYNC, "'%s' LAUNCH_BLOCKING memset completed [stream:%p].\n", __func__, (void*)stream); + } + } else { + e = hipErrorInvalidValue; + } + + return ihipLogStatus(e); } From a849321bd9a9fe6eefdc136c450f3c175fb5d481 Mon Sep 17 00:00:00 2001 From: bwicakso Date: Mon, 25 Apr 2016 14:42:35 -0500 Subject: [PATCH 46/56] Update with original --- hipamd/include/hcc_detail/hip_ldg.h | 1 + hipamd/tests/src/hip_test_ldg.cpp | 154 ++++++++++++++++++++++++++-- 2 files changed, 149 insertions(+), 6 deletions(-) diff --git a/hipamd/include/hcc_detail/hip_ldg.h b/hipamd/include/hcc_detail/hip_ldg.h index e6fe45cd77..4dab90b4e8 100644 --- a/hipamd/include/hcc_detail/hip_ldg.h +++ b/hipamd/include/hcc_detail/hip_ldg.h @@ -102,3 +102,4 @@ __device__ double4 __ldg(const double4* ); #endif // __HCC__ #endif // HIP_LDG_H + diff --git a/hipamd/tests/src/hip_test_ldg.cpp b/hipamd/tests/src/hip_test_ldg.cpp index a58652d240..31c7d4865a 100644 --- a/hipamd/tests/src/hip_test_ldg.cpp +++ b/hipamd/tests/src/hip_test_ldg.cpp @@ -26,7 +26,7 @@ THE SOFTWARE. #include #include "hip_runtime.h" #include "test_common.h" - +#if __hcc_workweek__ >= 16164 #define HIP_ASSERT(x) (assert((x)==hipSuccess)) @@ -149,14 +149,156 @@ int main() { cout << " System major " << devProp.major << endl; cout << " agent prop name " << devProp.name << endl; - int errors = dataTypesRun() & - dataTypesRun() & - dataTypesRun() & - dataTypesRun(); - //hipResetDefaultAccelerator(); + int errors; + + errors = dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Char"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Short"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Int"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Long"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Long Long"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Unsigned Char"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Unsigned Short"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Unsigned Int"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Unsigned Long Long"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + if(errors == 1){ + errors = 0; + }else{ + std::cout<<"Failed Float"<() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun() & + dataTypesRun(); + + + //hipResetDefaultAccelerator(); if(errors == 1){ passed(); return 0; + }else{ + std::cout<<"Failed Float"< Date: Mon, 25 Apr 2016 15:13:23 -0500 Subject: [PATCH 47/56] add hostname --- hipamd/bin/hipconfig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/hipamd/bin/hipconfig b/hipamd/bin/hipconfig index 08fb6baade..49c385753d 100755 --- a/hipamd/bin/hipconfig +++ b/hipamd/bin/hipconfig @@ -97,9 +97,9 @@ if (!$printed or $p_full) { print ("HSA_PATH : $HSA_PATH\n"); print ("HCC_HOME : $HCC_HOME\n"); system("$HCC_HOME/bin/hcc --version"); - print ("HCC-cxxflags: "); + print ("HCC-cxxflags : "); system("$HCC_HOME/bin/hcc-config --cxxflags"); - print ("HCC-ldflags : "); + print ("HCC-ldflags : "); system("$HCC_HOME/bin/hcc-config --ldflags"); printf("\n"); } @@ -119,6 +119,7 @@ if (!$printed or $p_full) { print "\n" ; print "== Linux Kernel\n"; + print "Hostname : "; system ("hostname"); system ("uname -a"); if (-e "/usr/bin/lsb_release") { From 87c355f09db0ae0bb5158cd4c7b2ff83067f04f0 Mon Sep 17 00:00:00 2001 From: Ben Sander Date: Wed, 27 Apr 2016 11:55:09 -0500 Subject: [PATCH 48/56] Add tip on making local HIP (mostly for HIP devs) --- hipamd/CONTRIBUTING.md | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/hipamd/CONTRIBUTING.md b/hipamd/CONTRIBUTING.md index 3b07c0c0c5..473a14a143 100644 --- a/hipamd/CONTRIBUTING.md +++ b/hipamd/CONTRIBUTING.md @@ -1,5 +1,18 @@ # Contributor Guidelines +## Make Tips +When building HIP, you will likely want to build and install to a local user-accessible directory (rather than /opt/rocm). +This can be easily be done by setting the -DCMAKE_INSTALL_PREFIX variable when running cmake. Typical use case is to +set CMAKE_INSTALL_PREFIX to your HIP git root, and then ensure HIP_PATH points to this directory. For example + +``` +cmake .. -DCMAKE_INSTALL_PREFIX=.. +make install + +export HIP_PATH= +``` + + ## Adding a new HIP API From 06df8bbfbc27bde8286915dccb83ed663e224991 Mon Sep 17 00:00:00 2001 From: Ben Sander Date: Wed, 27 Apr 2016 17:45:14 -0500 Subject: [PATCH 49/56] Doc update --- hipamd/CONTRIBUTING.md | 2 ++ hipamd/docs/markdown/hip_porting_guide.md | 5 +++-- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/hipamd/CONTRIBUTING.md b/hipamd/CONTRIBUTING.md index 473a14a143..f6e578efd8 100644 --- a/hipamd/CONTRIBUTING.md +++ b/hipamd/CONTRIBUTING.md @@ -12,6 +12,8 @@ make install export HIP_PATH= ``` +After making HIP, don't forget the "make install" step ! + ## Adding a new HIP API diff --git a/hipamd/docs/markdown/hip_porting_guide.md b/hipamd/docs/markdown/hip_porting_guide.md index 6c12547c2d..b706262f71 100644 --- a/hipamd/docs/markdown/hip_porting_guide.md +++ b/hipamd/docs/markdown/hip_porting_guide.md @@ -8,7 +8,7 @@ and provides practical suggestions on how to port CUDA code and work through com * [HIP Porting Guide](#hip-porting-guide) * [Table of Contents](#table-of-contents) - * [Porting a New Cuda Project TO](#porting-a-new-cuda-project) + * [Porting a New Cuda Project To HIP](#porting-a-new-cuda-project) * [General Tips](#general-tips" aria-hidden="true"> Date: Sat, 30 Apr 2016 12:11:04 -0500 Subject: [PATCH 51/56] removed warnings --- hipamd/src/hip_peer.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/hipamd/src/hip_peer.cpp b/hipamd/src/hip_peer.cpp index e81b27c31a..cec8017b0c 100644 --- a/hipamd/src/hip_peer.cpp +++ b/hipamd/src/hip_peer.cpp @@ -24,7 +24,7 @@ THE SOFTWARE. #include "hcc_detail/trace_helper.h" /** - * @warning HCC returns 0 in *canAccessPeer ; Need to update this function when RT supports P2P + * HCC returns 0 in *canAccessPeer ; Need to update this function when RT supports P2P */ //--- hipError_t hipDeviceCanAccessPeer (int* canAccessPeer, int deviceId, int peerDeviceId) @@ -145,7 +145,7 @@ hipError_t hipMemcpyPeer (void* dst, int dstDevice, const void* src, int srcDe /** - * @bug This function uses a synchronous copy + * This function uses a synchronous copy */ //--- hipError_t hipMemcpyPeerAsync (void* dst, int dstDevice, const void* src, int srcDevice, size_t sizeBytes, hipStream_t stream) From 5d7f1682f4007f236182409eec597340ea2b14fe Mon Sep 17 00:00:00 2001 From: Ben Sander Date: Mon, 2 May 2016 10:19:46 -0500 Subject: [PATCH 52/56] split INSTALL.md into separate file --- hipamd/INSTALL.md | 189 ++++++++++++++++++++++++++++++++++++++++++++++ hipamd/README.md | 127 +------------------------------ 2 files changed, 191 insertions(+), 125 deletions(-) create mode 100644 hipamd/INSTALL.md diff --git a/hipamd/INSTALL.md b/hipamd/INSTALL.md new file mode 100644 index 0000000000..dccbee2995 --- /dev/null +++ b/hipamd/INSTALL.md @@ -0,0 +1,189 @@ + + +**Installation** + +- [Installing pre-built packages:](#installing-pre-built-packages) + - [Prerequisites](#prerequisites) + - [AMD (hcc)](#amd-hcc) + - [NVIDIA (nvcc)](#nvidia-nvcc) + - [Verify your installation](#verify-your-installation) +- [Building HIP from source](#building-hip-from-source) + - [HCC Options](#hcc-options) + - [Using HIP with the AMD Native-GCN compiler.](#using-hip-with-the-amd-native-gcn-compiler) + - [Compiling CodeXL markers for HIP Functions](#compiling-codexl-markers-for-hip-functions) + - [Using clang-hipify](#using-clang-hipify) + - [Building](#building) + - [Running and using clang-hipify](#running-and-using-clang-hipify) + + + +# Installing pre-built packages + +HIP can be easily installed using pre-built binary packages using the package manager for your platform. + +## Prerequisites +HIP code can be developed either on AMD ROCm platform using hcc compiler, or a CUDA platform with nvcc installed: + +## AMD-hcc + +* Install the [rocm](http://gpuopen.com/getting-started-with-boltzmann-components-platforms-installation/) packages. Rocm will install all of the necessary components, including the kernel driver, runtime software, HCC compiler, and HIP. + +* Default paths and environment variables: + + * By default HIP looks for hcc in /opt/rocm/hcc (can be overridden by setting HCC_HOME environment variable) + * By default HIP looks for HSA in /opt/rocm/hsa (can be overridden by setting HSA_PATH environment variable) + * By default HIP is installed into /opt/rocm/hip (can be overridden by setting HIP_PATH environment variable). + * Optionally, consider adding /opt/rocm/bin to your path to make it easier to use the tools. + + +## NVIDIA-nvcc +* Configure the additional package server as described [here](http://gpuopen.com/getting-started-with-boltzmann-components-platforms-installation/). +* Install the "hip_nvcc" package. This will install CUDA SDK and the HIP porting layer. +``` +apt-get install hip_nvcc +``` + +* Default paths and environment variables: + * By default HIP looks for CUDA SDK in /usr/local/cuda (can be overriden by setting CUDA_PATH env variable) + * By default HIP is installed into /opt/rocm/hip (can be overridden by setting HIP_PATH environment variable). + * Optionally, consider adding /opt/rocm/bin to your path to make it easier to use the tools. + + +## Verify your installation +Run hipconfig (instructions below assume default installation path) : +```shell +/opt/rocm/bin/hipconfig --full +``` + +Compile and run the [square sample](https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP/tree/master/samples/0_Intro/square). + + +# Building HIP from source +HIP source code is available and the project can be built from source on the HCC platform. + +1. Follow the above steps to install and validate the binary packages. +2. Download HIP source code (from the [GitHub repot](https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP).) +3. Build and install HIP (This is the simple version assuming default paths ; see below for additional options.) +``` +cd HIP-privatestaging +mkdir build +cd build +cmake .. +make +make install +``` + +* Default paths: + * By default cmake looks for hcc in /opt/rocm/hcc (can be overridden by setting ```-DHCC_HOME=/path/to/hcc``` in the cmake step).* + * By default cmake looks for HSA in /opt/rocm/hsa (can be overridden by setting ```-DHSA_PATH=/path/to/hsa``` in the cmake step).* + * By default cmake installs HIP to /opt/rocm/hip (can be overridden by setting ```-DCMAKE_INSTALL_PREFIX=/where/to/install/hip``` in the cmake step).* + +Here's a richer command-line that overrides the default paths: + +```shell +cd HIP-privatestaging +mkdir build +cd build +cmake -DHSA_PATH=/path/to/hsa -DHCC_HOME=/path/to/hcc -DCMAKE_INSTALL_PREFIX=/where/to/install/hip -DCMAKE_BUILD_TYPE=Release .. +make +make install +``` + +* After installation, make sure HIP_PATH is pointed to `/where/to/install/hip`. + +## HCC Options + +### Using HIP with the AMD Native-GCN compiler. +AMD recently released a direct-to-GCN-ISA target. This compiler generates GCN ISA directly from LLVM, without going through an intermediate compiler +IR such as HSAIL or PTX. +The native GCN target is included with upstream LLVM, and has also been integrated with HCC compiler and can be used to compiler HIP programs for AMD. +Binary packages for the direct-to-isa package are included with the [rocm](http://gpuopen.com/getting-started-with-boltzmann-components-platforms-installation/) package. +Alternatively, this sections describes how to build it from source: + +1. Install the rocm packages as described above. +2. Follow the instructions [here](https://github.com/RadeonOpenCompute/HCC-Native-GCN-ISA/wiki) + * In the make step for HCC, we recommend setting -DCMAKE_INSTALL_PREFIX. + * Set HCC_HOME environment variable before compiling HIP program to point to the native compiler: +```shell +export HCC_HOME=/path/to/native/hcc +``` + + +### Compiling CodeXL markers for HIP Functions +HIP can generate markers at function begin/end which are displayed on the CodeXL timeline view. To do this, you need to install CodeXL, tell HIP +where the CodeXL install directory lives, and enable HIP to generate the markers: + +1. Install CodeXL +See [CodeXL Download](http://developer.amd.com/tools-and-sdks/opencl-zone/codexl/?webSyncID=9d9c2cb9-3d73-5e65-268a-c7b06428e5e0&sessionGUID=29beacd0-d654-ddc6-a3e2-b9e6c0b0cc77) for the installation file. +Also this [blog](http://gpuopen.com/getting-up-to-speed-with-the-codexl-gpu-profiler-and-radeon-open-compute/) provides more information and tips for using CodeXL. In addition to installing the CodeXL profiling +and visualization tools, CodeXL also comes with an SDK that allow applications to add markers to the timeline viewer. We'll be linking HIP against this library. + +2. Set CODEXL_PATH +```shell +# set to your code-xl installation location: +export CODEXL_PATH=/opt/AMD/CodeXL +``` + +3. Enable in source code. +In src/hip_hcc.cpp, enable the define +```c +#define COMPILE_TRACE_MARKER 1 +``` + + +Then recompile the target application, run with profiler enabled to generate ATP file or trace log. +```shell +# Use profiler to generate timeline view: +$CODEXL_PATH/CodeXLGpuProfiler -A -o ./myHipApp +... +Session output path: /home/me/HIP-privatestaging/tests/b1/mytrace.atp +``` + +You can also print the HIP function strings to stderr using HIP_TRACE_API environment variable. This can be useful for tracing application flow. Also can be combined with the more detailed debug information provided +by the HIP_DB switch. For example: +```shell +# Trace to stderr showing begin/end of each function (with arguments) + intermediate debug trace during the execution of each function. +HIP_TRACE_API=1 HIP_DB=0x2 ./myHipApp +``` + +Note this trace mode uses colors. "less -r" can handle raw control characters and will display the debug output in proper colors. + + +### Using clang-hipify + +Clang-hipify is a clang-based tool which can automate the translation of CUDA source code into portable HIP C++. +The clang-hipify tool can automatically add extra HIP arguments (notably the "hipLaunchParm" required at the +beginning of every HIP kernel call). Clang-hipify has some additional dependencies explained below and +can be built as a separate make step. + + +#### Building + +1. Download and unpack clang+llvm 3.8 binary package preqrequisite: +``` +wget http://llvm.org/releases/3.8.0/clang+llvm-3.8.0-x86_64-linux-gnu-ubuntu-14.04.tar.xz +tar xvfJ clang+llvm-3.8.0-x86_64-linux-gnu-ubuntu-14.04.tar.xz +``` + +2. Enable build of clang-hipify and specify path to LLVM: +Note LLVM_DIR must be a full absolute path (not relative) to the location extracted above. Here's an example assuming we +extract the clang 3.8 package into ~/HIP-privatestaging/clang+llvm-3.8.0-x86_64-linux-gnu-ubuntu-14.04/. +``` +cd HIP-privatestaging +mkdir build.clang-hipify +cd build.clang-hipify +cmake -DBUILD_CLANG_HIPIFY=1 -DLLVM_DIR=~/HIP-privatestaging/clang+llvm-3.8.0-x86_64-linux-gnu-ubuntu-14.04/ -DCMAKE_BUILD_TYPE=Release .. +make +make install +``` + +#### Running and using clang-hipify +clang-hipify performs an initial compile of the CUDA source code into a "symbol tree", and thus needs access to the appropriate header files: + 1. Download "deb(network)" variant of target installer from https://developer.nvidia.com/cuda-downloads. The commands below show how to download and install a recent version from the http://developer.download.nvidia.com/compute/cuda/repos/ubuntu1404/x86_64/cuda-repo-ubuntu1404_7.5-18_amd64.deb. + +``` +wget http://developer.download.nvidia.com/compute/cuda/repos/ubuntu1404/x86_64/cuda-repo-ubuntu1404_7.5-18_amd64.deb +sudo dpkg -i cuda-repo-ubuntu1404_7.5-18_amd64.deb +sudo apt-get update && sudo apt-get install cuda-minimal-build-7-5 cuda-curand-dev-7-5 +``` + diff --git a/hipamd/README.md b/hipamd/README.md index 2244c656cd..116d74e197 100644 --- a/hipamd/README.md +++ b/hipamd/README.md @@ -10,32 +10,9 @@ Key features include: * Developers can specialize for the platform (CUDA or hcc) to tune for performance or handle tricky cases New projects can be developed directly in the portable HIP C++ language and can run on either NVIDIA or AMD platforms. Additionally, HIP provides porting tools which make it easy to port existing CUDA codes to the HIP layer, with no loss of performance as compared to the original CUDA application. HIP is not intended to be a drop-in replacement for CUDA, and developers should expect to do some manual coding and performance tuning work to complete the port. -## Installation -```shell -cd HIP-privatestaging -mkdir build -cd build -<<<<<<< HEAD -cmake .. -make -make install -``` -*By default cmake looks for hcc in /opt/rocm/hcc (can be overridden by setting ```-DHCC_HOME=/path/to/hcc``` in the cmake step).* - -*By default cmake looks for HSA in /opt/rocm/hsa (can be overridden by setting ```-DHSA_PATH=/path/to/hsa``` in the cmake step).* - -*By default cmake installs HIP to /opt/rocm/hip (can be overridden by setting ```-DCMAKE_INSTALL_PREFIX=/where/to/install/hip``` in the cmake step).* - -*Make sure HIP_PATH is pointed to `/where/to/install/hip` and PATH includes `$HIP_PATH/bin`. This requirement is optional, but required to run any HIP test infrastructure.* -======= -cmake -DHSA_PATH=/path/to/hsa -DHCC_HOME=/path/to/hcc -DCMAKE_INSTALL_PREFIX=/where/to/install/hip -DLLVM_DIR=/path/to/clang-llvm-3.8 -DCMAKE_BUILD_TYPE=Release .. -make -make install -``` -Make sure HIP_PATH is pointed to `/where/to/install/hip` and PATH includes `$HIP_PATH/bin`. This requirement is optional, but required to run any HIP test infrastructure. The path `/path/to/clang-llvm-3.8` should be specified for [clang-hipify](README.md#clang-hipify) utility build. ->>>>>>> clang-hipify ## More Info: +- [Installation](INSTALL.md) and [clang-hipify](INSTALL.md#use-clang-hipify.md) - [HIP FAQ](docs/markdown/hip_faq.md) - [HIP Kernel Language](docs/markdown/hip_kernel_language.md) - [HIP Runtime API (Doxygen)](http://gpuopen-professionalcompute-tools.github.io/HIP) @@ -47,108 +24,8 @@ Make sure HIP_PATH is pointed to `/where/to/install/hip` and PATH includes `$HIP ## How do I get set up? -### Prerequisites - Choose Your Platform -HIP code can be developed either on AMD ROCm platform using hcc compiler, or a CUDA platform with nvcc installed: +See the [Installation](INSTALL.md) notes. -#### AMD (hcc): - -* Install [hcc](https://bitbucket.org/multicoreware/hcc/wiki/Home) including supporting HSA kernel and runtime driver stack -* By default HIP looks for hcc in /opt/rocm/hcc (can be overridden by setting HCC_HOME environment variable) -* By default HIP looks for HSA in /opt/rocm/hsa (can be overridden by setting HSA_PATH environment variable) -* Ensure that ROCR runtime is installed and added to LD_LIBRARY_PATH -* Install HIP (from this GitHub repot). By default HIP is installed into /opt/rocm/hip (can be overridden by setting HIP_PATH environment variable). - -* Optionally, consider adding /opt/rocm/bin to your path to make it easier to use the tools. - - -#####clang-hipify -To build and run clang based hipify utiliy a set of CUDA headers and clang+llvm 3.8 binary package are required: -- download and install CUDA minimal prerequisites: - 1. Download "deb(network)" variant of target installer from https://developer.nvidia.com/cuda-downloads. E.g. at the moment the link is http://developer.download.nvidia.com/compute/cuda/repos/ubuntu1404/x86_64/cuda-repo-ubuntu1404_7.5-18_amd64.deb - 2. install clang prerequisites with the following commands: -``` -wget http://developer.download.nvidia.com/compute/cuda/repos/ubuntu1404/x86_64/cuda-repo-ubuntu1404_7.5-18_amd64.deb -sudo dpkg -i cuda-repo-ubuntu1404_7.5-18_amd64.deb -sudo apt-get update && sudo apt-get install cuda-minimal-build-7-5 cuda-curand-dev-7-5 -``` -- download and unpack clang+llvm 3.8 binary package: -``` -wget http://llvm.org/releases/3.8.0/clang+llvm-3.8.0-x86_64-linux-gnu-ubuntu-14.04.tar.xz -tar xvfJ clang+llvm-3.8.0-x86_64-linux-gnu-ubuntu-14.04.tar.xz -C /path/to/clang-llvm-3.8 -``` -#### NVIDIA (nvcc) -* Install CUDA SDK from manufacturer website -* By default HIP looks for CUDA SDK in /usr/local/cuda (can be overriden by setting CUDA_PATH env variable) -* Install HIP (from this GitHub repot). By default HIP is installed into /opt/rocm/hip (can be overridden by setting HIP_PATH environment variable). - -* Optionally, consider adding /opt/rocm/bin to your path to make it easier to use the tools. - -#### Verify your installation -Run hipconfig (instructions below assume default installation path) : -```shell -/opt/rocm/bin/hipconfig --full -``` - -Compile and run the [square sample](https://github.com/GPUOpen-ProfessionalCompute-Tools/HIP/tree/master/samples/0_Intro/square). - - - -### HCC Options - -#### Compiling CodeXL markers for HIP Functions -HIP can generate markers at function begin/end which are displayed on the CodeXL timeline view. To do this, you need to install CodeXL, tell HIP -where the CodeXL install directory lives, and enable HIP to generate the markers: - -1. Install CodeXL -See [CodeXL Download](http://developer.amd.com/tools-and-sdks/opencl-zone/codexl/?webSyncID=9d9c2cb9-3d73-5e65-268a-c7b06428e5e0&sessionGUID=29beacd0-d654-ddc6-a3e2-b9e6c0b0cc77) for the installation file. -Also this [blog](http://gpuopen.com/getting-up-to-speed-with-the-codexl-gpu-profiler-and-radeon-open-compute/) provides more information and tips for using CodeXL. In addition to installing the CodeXL profiling -and visualization tools, CodeXL also comes with an SDK that allow applications to add markers to the timeline viewer. We'll be linking HIP against this library. - -2. Set CODEXL_PATH -```shell -# set to your code-xl installation location: -export CODEXL_PATH=/opt/AMD/CodeXL -``` - -3. Enable in source code. -In src/hip_hcc.cpp, enable the define -```c -#define COMPILE_TRACE_MARKER 1 -``` - - -Then recompile the target application, run with profiler enabled to generate ATP file or trace log. -```shell -# Use profiler to generate timeline view: -$CODEXL_PATH/CodeXLGpuProfiler -A -o ./myHipApp -... -Session output path: /home/me/HIP-privatestaging/tests/b1/mytrace.atp -``` - -You can also print the HIP function strings to stderr using HIP_TRACE_API environment variable. This can be useful for tracing application flow. Also can be combined with the more detailed debug information provided -by the HIP_DB switch. For example: -```shell -# Trace to stderr showing begin/end of each function (with arguments) + intermediate debug trace during the execution of each function. -HIP_TRACE_API=1 HIP_DB=0x2 ./myHipApp -``` - -Note this trace mode uses colors. "less -r" can handle raw control characters and will display the debug output in proper colors. - - -#### Using HIP with the AMD Native-GCN compiler. -AMD recently released a direct-to-GCN-ISA target. This compiler generates GCN ISA directly from LLVM, without going through an intermediate compiler -IR such as HSAIL or PTX. -The native GCN target is included with upstream LLVM, and has also been integrated with HCC compiler and can be used to compiler HIP programs for AMD. -Here's how to use it with HIP: - -- Follow the instructions here to compile the HCC and native LLVM compiler: -> https://github.com/RadeonOpenCompute/HCC-Native-GCN-ISA/wiki -> (In the make step for HCC, we recommend setting -DCMAKE_INSTALL_PREFIX=/opt/hcc-native) - -Set HCC_HOME environment variable before compiling HIP program to point to the native compiler: -```shell -export HCC_HOME=/opt/hcc-native -``` ## Examples and Getting Started: From 83cf3ed2b5a49504d71889dbb2d9a52ee571b4ac Mon Sep 17 00:00:00 2001 From: Ben Sander Date: Mon, 2 May 2016 10:20:00 -0500 Subject: [PATCH 53/56] Add clang-hipify as optional make step --- hipamd/CMakeLists.txt | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/hipamd/CMakeLists.txt b/hipamd/CMakeLists.txt index 7df6bed4db..13e6fb8485 100644 --- a/hipamd/CMakeLists.txt +++ b/hipamd/CMakeLists.txt @@ -8,7 +8,14 @@ set(HIP_VERSION_MAJOR "0") set(HIP_VERSION_MINOR "84") set(HIP_VERSION_PATCH "0") -add_subdirectory(clang-hipify) + +if(NOT DEFINED BUILD_CLANG_HIPIFY) + set(BUILD_CLANG_HIPIFY 0) +endif() + +if(BUILD_CLANG_HIPIFY) + add_subdirectory(clang-hipify) +endif() ############################# # Configure variables @@ -18,9 +25,10 @@ if(NOT DEFINED HIP_PLATFORM) if(NOT DEFINED ENV{HIP_PLATFORM}) execute_process(COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/bin/hipconfig --platform OUTPUT_VARIABLE HIP_PLATFORM + OUTPUT_STRIP_TRAILING_WHITESPACE) else() set(HIP_PLATFORM $ENV{HIP_PLATFORM} CACHE STRING "HIP Platform") - OUTPUT_STRIP_TRAILING_WHITESPACE) + endif() endif() message(STATUS "HIP Platform: " ${HIP_PLATFORM}) From c5bec313ee15a060869a62f021873f0564cd045e Mon Sep 17 00:00:00 2001 From: Ben Sander Date: Mon, 2 May 2016 11:33:22 -0500 Subject: [PATCH 54/56] Use hipconfig to determine platform --- hipamd/bin/hipcc | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/hipamd/bin/hipcc b/hipamd/bin/hipcc index f09e673e7c..a2ac421633 100755 --- a/hipamd/bin/hipcc +++ b/hipamd/bin/hipcc @@ -33,8 +33,6 @@ $HIP_PATH=dirname (dirname $0) unless defined $HIP_PATH; # use parent dir #print "HIP_PATH=$HIP_PATH\n"; -$CUDA_PATH=$ENV{'CUDA_PATH'}; -$CUDA_PATH='/usr/local/cuda' unless defined $CUDA_PATH; $CODEXL_PATH = $ENV{'CODEXL_PATH'}; $CODEXL_PATH = "/opt/AMD/CodeXL" unless defined $CODEXL_PATH; @@ -42,17 +40,14 @@ $marker_path = "$CODEXL_PATH/SDK/AMDTActivityLogger"; #--- #HIP_PLATFORM controls whether to use NVCC or HCC for compilation: -$HIP_PLATFORM=$ENV{'HIP_PLATFORM'}; -if (not defined $HIP_PLATFORM and (-e "$CUDA_PATH/bin/nvcc")) { - $HIP_PLATFORM="nvcc"; -} +$HIP_PLATFORM= `$HIP_PATH/bin/hipconfig --platform`; + $HIP_PLATFORM="hcc" unless defined $HIP_PLATFORM; if ($verbose & 0x2) { print ("HIP_PATH=$HIP_PATH\n"); print ("HIP_PLATFORM=$HIP_PLATFORM\n"); - print ("CUDA_PATH=$CUDA_PATH\n"); } $enablestdcpplib = 0; @@ -104,6 +99,11 @@ if ($HIP_PLATFORM eq "hcc") { } } elsif ($HIP_PLATFORM eq "nvcc") { + if ($verbose & 0x2) { + print ("CUDA_PATH=$CUDA_PATH\n"); + } + $CUDA_PATH=$ENV{'CUDA_PATH'}; + $CUDA_PATH='/usr/local/cuda' unless defined $CUDA_PATH; $HIPCC="$CUDA_PATH/bin/nvcc"; $HIPCXXFLAGS .= " -I$CUDA_PATH/include"; From aea31ad4e1db68cc097508f0c05978dcc1a44613 Mon Sep 17 00:00:00 2001 From: Ben Sander Date: Mon, 2 May 2016 12:49:53 -0500 Subject: [PATCH 55/56] Explicitly include --- hipamd/tests/src/hipEnvVarDriver.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/hipamd/tests/src/hipEnvVarDriver.cpp b/hipamd/tests/src/hipEnvVarDriver.cpp index 245b23b52e..b5cab268b7 100644 --- a/hipamd/tests/src/hipEnvVarDriver.cpp +++ b/hipamd/tests/src/hipEnvVarDriver.cpp @@ -20,6 +20,8 @@ THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include #include #include +#include + using namespace std; //./hipEnvVar -c -d 0 -h From a398cd4cdaae7852faab9953e72a23487a4fb11b Mon Sep 17 00:00:00 2001 From: Ben Sander Date: Mon, 2 May 2016 13:37:14 -0500 Subject: [PATCH 56/56] PASS with warning if not enough GPUs detected. --- hipamd/tests/src/hipMemcpyAll.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/hipamd/tests/src/hipMemcpyAll.cpp b/hipamd/tests/src/hipMemcpyAll.cpp index c8484aa32f..49e7c94bdf 100644 --- a/hipamd/tests/src/hipMemcpyAll.cpp +++ b/hipamd/tests/src/hipMemcpyAll.cpp @@ -40,6 +40,8 @@ int num; hipGetDeviceCount(&num); if(num < 2) { + printf ("warning: Not enough GPUs to run the test, exiting without running.\n"); + passed(); return 0; }