20 :
m_env (
std::make_unique<
Ort::Env>(ORT_LOGGING_LEVEL_FATAL,
""))
23 Ort::SessionOptions session_options;
24 session_options.SetIntraOpNumThreads(1);
28 session_options.SetLogSeverityLevel(4);
29 session_options.SetGraphOptimizationLevel(
30 GraphOptimizationLevel::ORT_ENABLE_EXTENDED);
33 session_options.AddConfigEntry(
34 kOrtSessionOptionsDisableSpecifiedOptimizers,
"QuickGeluFusion");
42 session_options.DisableCpuMemArena();
46 if (opts.execution_provider ==
"CUDA") {
47 Ort::CUDAProviderOptions cuda_options;
49 {
"device_id", std::to_string(opts.device_id)},
52 {
"use_tf32", opts.use_tf32 ?
"1" :
"0"},
54 session_options.AppendExecutionProvider_CUDA_V2(*cuda_options);
55 }
else if (opts.execution_provider !=
"CPU") {
56 throw std::runtime_error(
57 "unknown execution provider '" + opts.execution_provider +
"'");
61 Ort::AllocatorWithDefaultOptions allocator;
64 m_session = std::make_unique<Ort::Session>(
65 *m_env, path_to_onnx.c_str(), session_options);
68 m_metadata = loadMetadata(
"gnn_config");
69 m_num_inputs = m_session->GetInputCount();
70 m_num_outputs = m_session->GetOutputCount();
73 if (m_metadata.contains(
"onnx_model_version")) {
74 m_onnx_model_version = m_metadata[
"onnx_model_version"].get<
SaltModelVersion>();
76 throw std::runtime_error(
"Unknown Onnx model version!");
82 throw std::runtime_error(
"Onnx model version not found in metadata");
87 m_model_name = determineModelName();
90 for (
size_t i = 0;
i < m_num_inputs;
i++) {
91 m_input_node_names.push_back(m_session->GetInputNameAllocated(i, allocator).get());
95 for (
size_t i = 0;
i < m_num_outputs;
i++) {
96 const auto name = std::string(m_session->GetOutputNameAllocated(i, allocator).get());
97 const auto type = m_session->GetOutputTypeInfo(i).GetTensorTypeAndShapeInfo().GetElementType();
98 const int rank = m_session->GetOutputTypeInfo(i).GetTensorTypeAndShapeInfo().GetShape().size();
100 m_output_nodes.emplace_back(name, type, m_model_name);
102 m_output_nodes.emplace_back(name, type, rank);
115 Ort::AllocatorWithDefaultOptions allocator;
118 return std::string(
m_metadata[
"outputs"].begin().key());
122 std::set<std::string> model_names;
124 const auto name = std::string(
m_session->GetOutputNameAllocated(i, allocator).get());
125 size_t underscore_pos = name.find(
'_');
126 if (underscore_pos != std::string::npos) {
127 model_names.insert(name.substr(0, underscore_pos));
129 return std::string(
"");
132 if (model_names.size() != 1) {
133 throw std::runtime_error(
"SaltModel: model names are not consistent between outputs");
135 return *model_names.begin();
159 std::vector<float> input_tensor_values;
162 auto memory_info = Ort::MemoryInfo::CreateCpu(
163 OrtArenaAllocator, OrtMemTypeDefault
165 std::vector<Ort::Value> input_tensors;
167 input_tensors.push_back(Ort::Value::CreateTensor<float>(
168 memory_info, gnn_inputs.at(node_name).first.data(), gnn_inputs.at(node_name).first.size(),
169 gnn_inputs.at(node_name).second.data(), gnn_inputs.at(node_name).second.size())
174 std::vector<const char*> input_node_names;
177 input_node_names.push_back(name.c_str());
179 std::vector<const char*> output_node_names;
182 output_node_names.push_back(
node.name_in_model.c_str());
190 auto output_tensors = session.Run(Ort::RunOptions{
nullptr},
191 input_node_names.data(), input_tensors.data(), input_node_names.size(),
192 output_node_names.data(), output_node_names.size()
197 for (
size_t node_idx = 0; node_idx <
m_output_nodes.size(); ++node_idx) {
199 const auto& tensor = output_tensors[node_idx];
200 auto tensor_type = tensor.GetTypeInfo().GetTensorTypeAndShapeInfo().GetElementType();
201 auto tensor_shape = tensor.GetTypeInfo().GetTensorTypeAndShapeInfo().GetShape();
202 int length = tensor.GetTensorTypeAndShapeInfo().GetElementCount();
203 if (tensor_type == ONNX_TENSOR_ELEMENT_DATA_TYPE_FLOAT) {
204 if (tensor_shape.size() == 0) {
205 output.singleFloat[output_node.name] = *tensor.GetTensorData<
float>();
206 }
else if (tensor_shape.size() == 1) {
207 const float* data = tensor.GetTensorData<
float>();
208 output.vecFloat[output_node.name] = std::vector<float>(data, data +
length);
210 throw std::runtime_error(
"Unsupported tensor shape for FLOAT type");
212 }
else if (tensor_type == ONNX_TENSOR_ELEMENT_DATA_TYPE_INT8) {
213 if (tensor_shape.size() == 1) {
214 const char* data = tensor.GetTensorData<
char>();
215 output.vecChar[output_node.name] = std::vector<char>(data, data +
length);
217 throw std::runtime_error(
"Unsupported tensor shape for INT8 type");
220 throw std::runtime_error(
"Unsupported tensor type");