mirror of
https://github.com/intel/compute-runtime.git
synced 2025-12-30 01:35:20 +08:00
Zebin: set kernel barriers based on ext funcs
This change allows for modifying kernel's barrier count based on called external functions metadata passed via zeInfo section in zebin. Added parsing external functions metadata. Added resolving external functions call graph. Added updating kernel barriers based on called external functions. Added support for L0 dynamic link. Signed-off-by: Krystian Chmielewski <krystian.chmielewski@intel.com>
This commit is contained in:
committed by
Compute-Runtime-Automation
parent
bae9e6f5b5
commit
0ccce5a6d7
@@ -55,6 +55,7 @@ static constexpr ConstStringRef zeInfo = ".ze_info";
|
||||
static constexpr ConstStringRef gtpinInfo = ".gtpin_info";
|
||||
static constexpr ConstStringRef noteIntelGT = ".note.intelgt.compat";
|
||||
static constexpr ConstStringRef vIsaAsmPrefix = ".visaasm.";
|
||||
static constexpr ConstStringRef externalFunctions = "Intel_Symbol_Table_Void_Program";
|
||||
} // namespace SectionsNamesZebin
|
||||
|
||||
static constexpr ConstStringRef IntelGtNoteOwnerName = "IntelGT";
|
||||
@@ -158,6 +159,8 @@ namespace Tags {
|
||||
static constexpr ConstStringRef kernels("kernels");
|
||||
static constexpr ConstStringRef version("version");
|
||||
static constexpr ConstStringRef globalHostAccessTable("global_host_access_table");
|
||||
static constexpr ConstStringRef functions("functions");
|
||||
|
||||
namespace Kernel {
|
||||
static constexpr ConstStringRef name("name");
|
||||
static constexpr ConstStringRef executionEnv("execution_env");
|
||||
@@ -279,10 +282,18 @@ static constexpr ConstStringRef hasNonKernelArgStore("has_non_kernel_arg_store")
|
||||
static constexpr ConstStringRef hasNonKernelArgAtomic("has_non_kernel_arg_atomic");
|
||||
} // namespace ExperimentalProperties
|
||||
} // namespace Kernel
|
||||
|
||||
namespace GlobalHostAccessTable {
|
||||
static constexpr ConstStringRef deviceName("device_name");
|
||||
static constexpr ConstStringRef hostName("host_name");
|
||||
} // namespace GlobalHostAccessTable
|
||||
|
||||
namespace Function {
|
||||
static constexpr ConstStringRef name("name");
|
||||
static constexpr ConstStringRef executionEnv("execution_env");
|
||||
using namespace Kernel::ExecutionEnv;
|
||||
} // namespace Function
|
||||
|
||||
} // namespace Tags
|
||||
|
||||
namespace Types {
|
||||
@@ -540,6 +551,12 @@ struct globalHostAccessTableT {
|
||||
std::string hostName;
|
||||
};
|
||||
} // namespace GlobalHostAccessTable
|
||||
|
||||
namespace Function {
|
||||
namespace ExecutionEnv {
|
||||
using namespace Kernel::ExecutionEnv;
|
||||
}
|
||||
} // namespace Function
|
||||
} // namespace Types
|
||||
|
||||
} // namespace ZebinKernelMetadata
|
||||
|
||||
@@ -1238,6 +1238,38 @@ NEO::DecodeError populateZeInfoVersion(NEO::Elf::ZebinKernelMetadata::Types::Ver
|
||||
return NEO::DecodeError::Success;
|
||||
}
|
||||
|
||||
NEO::DecodeError populateExternalFunctionsMetadata(NEO::ProgramInfo &dst, NEO::Yaml::YamlParser &yamlParser, const NEO::Yaml::Node &functionNd, std::string &outErrReason, std::string &outWarning) {
|
||||
ConstStringRef functionName;
|
||||
NEO::Elf::ZebinKernelMetadata::Types::Function::ExecutionEnv::ExecutionEnvBaseT execEnv = {};
|
||||
bool isValid = true;
|
||||
|
||||
for (const auto &functionMetadataNd : yamlParser.createChildrenRange(functionNd)) {
|
||||
auto key = yamlParser.readKey(functionMetadataNd);
|
||||
if (NEO::Elf::ZebinKernelMetadata::Tags::Function::name == key) {
|
||||
functionName = yamlParser.readValueNoQuotes(functionMetadataNd);
|
||||
} else if (NEO::Elf::ZebinKernelMetadata::Tags::Function::executionEnv == key) {
|
||||
auto execEnvErr = readZeInfoExecutionEnvironment(yamlParser, functionMetadataNd, execEnv, "external functions", outErrReason, outWarning);
|
||||
if (execEnvErr != DecodeError::Success) {
|
||||
isValid = false;
|
||||
}
|
||||
} else {
|
||||
outWarning.append("DeviceBinaryFormat::Zebin::" + NEO::Elf::SectionsNamesZebin::zeInfo.str() + " : Unknown entry \"" + yamlParser.readKey(functionMetadataNd).str() + "\" in context of : external functions\n");
|
||||
}
|
||||
}
|
||||
|
||||
if (isValid) {
|
||||
NEO::ExternalFunctionInfo extFunInfo;
|
||||
extFunInfo.functionName = functionName.str();
|
||||
extFunInfo.barrierCount = static_cast<uint8_t>(execEnv.barrierCount);
|
||||
extFunInfo.numGrfRequired = static_cast<uint16_t>(execEnv.grfCount);
|
||||
extFunInfo.simdSize = static_cast<uint8_t>(execEnv.simdSize);
|
||||
dst.externalFunctions.push_back(extFunInfo);
|
||||
return DecodeError::Success;
|
||||
} else {
|
||||
return DecodeError::InvalidBinary;
|
||||
}
|
||||
}
|
||||
|
||||
template <>
|
||||
DecodeError decodeSingleDeviceBinary<NEO::DeviceBinaryFormat::Zebin>(ProgramInfo &dst, const SingleDeviceBinary &src, std::string &outErrReason, std::string &outWarning) {
|
||||
auto elf = Elf::decodeElf<Elf::EI_CLASS_64>(src.deviceBinary, outErrReason, outWarning);
|
||||
@@ -1299,17 +1331,17 @@ DecodeError decodeSingleDeviceBinary<NEO::DeviceBinaryFormat::Zebin>(ProgramInfo
|
||||
UniqueNode kernelsSectionNodes;
|
||||
UniqueNode versionSectionNodes;
|
||||
UniqueNode globalHostAccessTableNodes;
|
||||
UniqueNode functionsSectionNodes;
|
||||
for (const auto &globalScopeNd : yamlParser.createChildrenRange(*yamlParser.getRoot())) {
|
||||
auto key = yamlParser.readKey(globalScopeNd);
|
||||
if (NEO::Elf::ZebinKernelMetadata::Tags::kernels == key) {
|
||||
kernelsSectionNodes.push_back(&globalScopeNd);
|
||||
continue;
|
||||
} else if (NEO::Elf::ZebinKernelMetadata::Tags::version == key) {
|
||||
versionSectionNodes.push_back(&globalScopeNd);
|
||||
continue;
|
||||
} else if (NEO::Elf::ZebinKernelMetadata::Tags::globalHostAccessTable == key) {
|
||||
globalHostAccessTableNodes.push_back(&globalScopeNd);
|
||||
continue;
|
||||
} else if (NEO::Elf::ZebinKernelMetadata::Tags::functions == key) {
|
||||
functionsSectionNodes.push_back(&globalScopeNd);
|
||||
} else {
|
||||
outWarning.append("DeviceBinaryFormat::Zebin::" + NEO::Elf::SectionsNamesZebin::zeInfo.str() + " : Unknown entry \"" + yamlParser.readKey(globalScopeNd).str() + "\" in global scope of " + NEO::Elf::SectionsNamesZebin::zeInfo.str() + "\n");
|
||||
}
|
||||
@@ -1368,6 +1400,20 @@ DecodeError decodeSingleDeviceBinary<NEO::DeviceBinaryFormat::Zebin>(ProgramInfo
|
||||
}
|
||||
}
|
||||
|
||||
if (functionsSectionNodes.size() > 1U) {
|
||||
outErrReason.append("DeviceBinaryFormat::Zebin::" + NEO::Elf::SectionsNamesZebin::zeInfo.str() + " : Expected at most one " + NEO::Elf::ZebinKernelMetadata::Tags::functions.str() + " entry in global scope of " + NEO::Elf::SectionsNamesZebin::zeInfo.str() + ", got : " + std::to_string(functionsSectionNodes.size()) + "\n");
|
||||
return DecodeError::InvalidBinary;
|
||||
}
|
||||
|
||||
if (false == functionsSectionNodes.empty()) {
|
||||
for (const auto &functionNd : yamlParser.createChildrenRange(*functionsSectionNodes[0])) {
|
||||
auto zeInfoErr = populateExternalFunctionsMetadata(dst, yamlParser, functionNd, outErrReason, outWarning);
|
||||
if (DecodeError::Success != zeInfoErr) {
|
||||
return zeInfoErr;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return DecodeError::Success;
|
||||
}
|
||||
|
||||
|
||||
@@ -117,4 +117,6 @@ NEO::DecodeError populateKernelDescriptor(NEO::ProgramInfo &dst, NEO::Elf::Elf<N
|
||||
|
||||
NEO::DecodeError populateZeInfoVersion(NEO::Elf::ZebinKernelMetadata::Types::Version &dst,
|
||||
NEO::Yaml::YamlParser &yamlParser, const NEO::Yaml::Node &versionNd, std::string &outErrReason, std::string &outWarning);
|
||||
|
||||
NEO::DecodeError populateExternalFunctionsMetadata(NEO::ProgramInfo &dst, NEO::Yaml::YamlParser &yamlParser, const NEO::Yaml::Node &functionNd, std::string &outErrReason, std::string &outWarning);
|
||||
} // namespace NEO
|
||||
|
||||
Reference in New Issue
Block a user