P4 to Git Change 1083876 by emankov@em-hsa-amd on 2014/10/03 04:25:16
ECR #333753 - HSA RT/Compiler Lib/Performance: Elimination of HSAIL text usage in RT Extracting HSAIL from the binary and parsing it for the kernel names in RT were replaced with aclQueryInfo call for RT_KERNEL_NAMES. Kernel names are obtained now from the corresponding metadata symbols names, which are already presented in BIF at kernel finalization stage. Side effect: performance improvement Next Step: Performance: elimination of BRIG disassembling to HSAIL as obligatory stage in Compiler Lib (previously was needed only by RT). Testing: pre check-in, ocl conformnace 2.0 (basic, api, compiler, workgroups, device_execution) Reviewers: Stanislav Mekhanoshin, German Andryeyev, Brian Sumner Affected files ... ... //depot/stg/opencl/drivers/opencl/compiler/lib/api/v0_8/acl.cpp#20 edit ... //depot/stg/opencl/drivers/opencl/compiler/lib/backends/common/v0_8/if_acl.cpp#51 edit ... //depot/stg/opencl/drivers/opencl/compiler/lib/include/v0_8/aclEnums.h#13 edit ... //depot/stg/opencl/drivers/opencl/compiler/lib/loaders/bif/bifbase.cpp#50 edit ... //depot/stg/opencl/drivers/opencl/compiler/lib/loaders/bif/bifbase.hpp#22 edit ... //depot/stg/opencl/drivers/opencl/compiler/lib/utils/v0_8/libUtils.h#11 edit ... //depot/stg/opencl/drivers/opencl/runtime/device/gpu/gpukernel.cpp#266 edit ... //depot/stg/opencl/drivers/opencl/runtime/device/gpu/gpuprogram.cpp#179 edit ... //depot/stg/opencl/drivers/opencl/tests/ocltst/module/complib/CLEnumCheck.cpp#37 edit
Этот коммит содержится в:
@@ -15,6 +15,7 @@
|
||||
#include <sstream>
|
||||
#include <cstdio>
|
||||
#include "utils/options.hpp"
|
||||
#include "utils/libUtils.h"
|
||||
#include "newcore.h"
|
||||
|
||||
extern "C" bool
|
||||
@@ -2159,76 +2160,50 @@ HSAILProgram::linkImpl(amd::option::Options* options)
|
||||
buildLog_ += "Error while BRIG Codegen phase: loading BRIG globals in the ELF \n";
|
||||
return false;
|
||||
}
|
||||
// We need to pull out kernels' names for finalizing kernels
|
||||
//! @todo Rewrite the below code, if another way to obtain kernel names
|
||||
//! appears in the compiler library
|
||||
size_t hsailSize = 0;
|
||||
const oclBIFSymbolStruct* symbol = findBIF30SymStruct(symHSAILText);
|
||||
assert(symbol && "symbol not found");
|
||||
std::string symName = symbol->str[PRE] + std::string("main") + symbol->str[POST];
|
||||
const void *hsailText = aclExtractSymbol(dev().hsaCompiler(), binaryElf_,
|
||||
&hsailSize, aclCODEGEN, symName.c_str(), &errorCode);
|
||||
size_t kernelNamesSize = 0;
|
||||
errorCode = aclQueryInfo(dev().hsaCompiler(), binaryElf_, RT_KERNEL_NAMES, NULL, NULL, &kernelNamesSize);
|
||||
if (errorCode != ACL_SUCCESS) {
|
||||
buildLog_ += "Error while reading out the HSAIL from the ELF \n" ;
|
||||
buildLog_ += "Error while Finalization phase: kernel names query from the ELF failed\n";
|
||||
return false;
|
||||
}
|
||||
std::string hsailProgram((char *)hsailText, hsailSize);
|
||||
HSAILProgram_ = hsailProgram;
|
||||
if (!HSAILProgram_.empty()) {
|
||||
bool dynamicParallelism = false;
|
||||
// Find out the name of the kernel. Works for multiple kernels
|
||||
int pos = 0;
|
||||
while (true) {
|
||||
std::string findString = "kernel &";
|
||||
size_t kernelNPos = HSAILProgram_.find(findString, pos);
|
||||
if (kernelNPos == std::string::npos) {
|
||||
break;
|
||||
}
|
||||
size_t kernelEndNPos = HSAILProgram_.find("l(", kernelNPos);
|
||||
pos = kernelEndNPos + 1;
|
||||
if (kernelEndNPos == std::string::npos) {
|
||||
break;
|
||||
}
|
||||
// "kernel &" is 8
|
||||
// "__OpenCL_" is 9
|
||||
// "_kerne" is 6
|
||||
// We can drop all this with a compiler tweak later
|
||||
std::string kernelName = HSAILProgram_.substr(kernelNPos + 8 + 9,
|
||||
kernelEndNPos -
|
||||
(kernelNPos + 8 + 9) - 6);
|
||||
HSAILKernel *aKernel = new HSAILKernel(kernelName, this,
|
||||
options->origOptionStr + hsailOptions());
|
||||
if (kernelNamesSize > 0) {
|
||||
char* kernelNames = new char[kernelNamesSize];
|
||||
errorCode = aclQueryInfo(dev().hsaCompiler(), binaryElf_, RT_KERNEL_NAMES, NULL, kernelNames, &kernelNamesSize);
|
||||
if (errorCode != ACL_SUCCESS) {
|
||||
buildLog_ += "Error while Finalization phase: kernel's Metadata is corrupted in the ELF\n";
|
||||
delete kernelNames;
|
||||
return false;
|
||||
}
|
||||
std::vector<std::string> vKernels = splitSpaceSeparatedString(kernelNames);
|
||||
delete kernelNames;
|
||||
std::vector<std::string>::iterator it = vKernels.begin();
|
||||
bool dynamicParallelism = false;
|
||||
for (it; it != vKernels.end(); ++it) {
|
||||
std::string kernelName = *it;
|
||||
HSAILKernel *aKernel = new HSAILKernel(kernelName, this, options->origOptionStr + hsailOptions());
|
||||
if (!aKernel->init(finalize)) {
|
||||
return false;
|
||||
}
|
||||
buildLog_ += aKernel->buildLog();
|
||||
aKernel->setUniformWorkGroupSize(options
|
||||
->oVariables->UniformWorkGroupSize);
|
||||
aKernel->setUniformWorkGroupSize(options->oVariables->UniformWorkGroupSize);
|
||||
kernels()[kernelName] = aKernel;
|
||||
dynamicParallelism |= aKernel->dynamicParallelism();
|
||||
// Find max scratch regs used in the program
|
||||
// It's used for scratch buffer preallocation with
|
||||
// dynamic parallelism, since runtime doesn't know
|
||||
// which child kernel will be called
|
||||
maxScratchRegs_ = std::max(
|
||||
static_cast<uint>(aKernel->workGroupInfo()->scratchRegs_),
|
||||
maxScratchRegs_);
|
||||
// Find max scratch regs used in the program. It's used for scratch buffer preallocation
|
||||
// with dynamic parallelism, since runtime doesn't know which child kernel will be called
|
||||
maxScratchRegs_ = std::max(static_cast<uint>(aKernel->workGroupInfo()->scratchRegs_), maxScratchRegs_);
|
||||
}
|
||||
|
||||
// Allocate kernel table for device enqueuing
|
||||
if (dynamicParallelism && !allocKernelTable()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Save the binary in the interface class
|
||||
size_t size = 0;
|
||||
void *mem = NULL;
|
||||
aclWriteToMem(binaryElf_, &mem, &size);
|
||||
setBinary(static_cast<char*>(mem), size);
|
||||
buildLog_ += aclGetCompilerLog(dev().hsaCompiler());
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
// Save the binary in the interface class
|
||||
size_t size = 0;
|
||||
void *mem = NULL;
|
||||
aclWriteToMem(binaryElf_, &mem, &size);
|
||||
setBinary(static_cast<char*>(mem), size);
|
||||
buildLog_ += aclGetCompilerLog(dev().hsaCompiler());
|
||||
return true;
|
||||
}
|
||||
|
||||
bool
|
||||
|
||||
Ссылка в новой задаче
Block a user