Skip to content

Commit eb559b6

Browse files
committed
TensorRT 7.2.1 open source release
Signed-off-by: Kevin Chen <kevinch@nvidia.com>
1 parent a3a4e38 commit eb559b6

24 files changed

Lines changed: 1319 additions & 1313 deletions

CMakeLists.txt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -42,8 +42,8 @@ set(PARSER_LINKER_SCRIPT ${ONNX2TRT_ROOT}/libnvonnxparser.version)
4242
# Version information
4343
#--------------------------------------------------
4444
set(ONNX2TRT_MAJOR 7)
45-
set(ONNX2TRT_MINOR 1)
46-
set(ONNX2TRT_PATCH 0)
45+
set(ONNX2TRT_MINOR 2)
46+
set(ONNX2TRT_PATCH 1)
4747

4848
#--------------------------------------------------
4949
# Build configurations, global to all projects

Changelog.md

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
# ONNX-TensorRT Changelog
2+
3+
## TensorRT 7.2.1 Release - 2020-10-20
4+
5+
### Added
6+
- Added support for parsing large models with external data
7+
- Added API for interfacing with TensorRT's refit feature
8+
- Updated `onnx_tensorrt` backend to support dynamic shapes
9+
- Added support for 3D instance normalizations [#515](https://github.com/onnx/onnx-tensorrt/pull/515)
10+
- Improved clarity on the resize modes TRT supports [#512](https://github.com/onnx/onnx-tensorrt/pull/521)
11+
- Added Changelog
12+
13+
### Changed
14+
- Unified docker usage between ONNX-TensorRT and TensorRT.
15+
16+
## Removed
17+
- Removed deprecated docker files.
18+
- Removed deprecated `setup.py`.
19+

ImporterContext.hpp

Lines changed: 35 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -26,12 +26,11 @@
2626
#include "onnx2trt_utils.hpp"
2727

2828
#include <list>
29-
#include <set>
30-
#include <string>
3129
#include <unordered_map>
3230

3331
namespace onnx2trt
3432
{
33+
3534
class ImporterContext final : public IImporterContext
3635
{
3736
nvinfer1::INetworkDefinition* _network;
@@ -45,22 +44,20 @@ class ImporterContext final : public IImporterContext
4544
StringMap<float> mTensorRangeMins;
4645
StringMap<float> mTensorRangeMaxes;
4746
StringMap<nvinfer1::DataType> mLayerPrecisions;
48-
std::set<std::string> mTensorNames; // keep track of tensor names used so far,
49-
// to avoid duplicate naming in TRT.
50-
std::set<std::string> mLayerNames; // keep track of layer names used so far,
51-
// to avoid duplicate naming in TRT.
52-
int64_t mSuffixCounter = 0; // increasing suffix counter used to uniquify layer names.
53-
std::unordered_set<std::string> mUnsupportedShapeTensors; // Container to hold any shape tensors that are
54-
// the output of layers that do not support
55-
// shape tensors.
56-
StringMap<std::string> mLoopTensors; // Container to map subgraph tensors to
57-
// their original outer graph names.
58-
std::string mOnnxFileLocation; // Keep track of the directory of the parsed ONNX file
47+
std::set<std::string> mTensorNames; // Keep track of how many times a tensor name shows up, to avoid duplicate naming in TRT.
48+
std::set<std::string> mLayerNames; // Keep track of how many times a tensor name shows up, to avoid duplicate naming in TRT.
49+
int64_t mSuffixCounter = 0; // increasing suffix counter used to uniquify layer names.
50+
std::unordered_set<std::string> mUnsupportedShapeTensors; // Container to hold output tensor names of layers that produce shape tensor outputs but do not natively support them.
51+
StringMap<std::string> mLoopTensors; // Container to map subgraph tensors to their original outer graph names.
52+
std::string mOnnxFileLocation; // Keep track of the directory of the parsed ONNX file
53+
std::list<std::string> mInitializerNames; // Keep track of unique names of any initializers
54+
RefitMap_t* mRefitMap; // Keep track of names of ONNX refittable weights with their corresponding TRT layer and role
5955

6056
public:
61-
ImporterContext(nvinfer1::INetworkDefinition* network, nvinfer1::ILogger* logger)
57+
ImporterContext(nvinfer1::INetworkDefinition* network, nvinfer1::ILogger* logger, RefitMap_t* refitMap)
6258
: _network(network)
6359
, _logger(logger)
60+
, mRefitMap(refitMap)
6461
{
6562
}
6663
virtual nvinfer1::INetworkDefinition* network() override
@@ -103,8 +100,11 @@ class ImporterContext final : public IImporterContext
103100
{
104101
return mOnnxFileLocation;
105102
}
106-
// This actually handles weights as well, but is named this way to be
107-
// consistent with the tensors()
103+
virtual void insertRefitMap(std::string weightsName, std::string layerName, nvinfer1::WeightsRole role) override
104+
{
105+
(*mRefitMap)[weightsName] = WeightsPair_t{layerName, role};
106+
}
107+
// This actually handles weights as well, but is named this way to be consistent with the tensors()
108108
virtual void registerTensor(TensorOrWeights tensor, const std::string& basename) override
109109
{
110110
// TRT requires unique tensor names.
@@ -119,16 +119,20 @@ class ImporterContext final : public IImporterContext
119119

120120
LOG_VERBOSE("Registering tensor: " << uniqueName << " for ONNX tensor: " << basename);
121121
}
122-
else if (tensor.is_weights() && tensor.weights().type == ::ONNX_NAMESPACE::TensorProto::INT64)
122+
else if (tensor.is_weights())
123123
{
124+
mInitializerNames.push_back(uniqueName);
124125
const auto& weights = tensor.weights();
125-
tensor = ShapedWeights{::ONNX_NAMESPACE::TensorProto::INT32,
126-
convertINT64(reinterpret_cast<int64_t*>(weights.values), weights.shape, ctx), weights.shape};
126+
if (tensor.weights().type == ::ONNX_NAMESPACE::TensorProto::INT64)
127+
{
128+
tensor = ShapedWeights{::ONNX_NAMESPACE::TensorProto::INT32,
129+
convertINT64(reinterpret_cast<int64_t*>(weights.values), weights.shape, ctx), weights.shape};
130+
}
131+
tensor.weights().setName(mInitializerNames.back().c_str());
127132
}
128133
}
129-
// Overwrite previous tensors registered with the same name (this only
130-
// happens when there are subgraphs, and in that case, overwriting is the
131-
// desired behavior).
134+
// Overwrite previous tensors registered with the same name (this only happens when there are subgraphs,
135+
// and in that case, overwriting is the desired behavior).
132136
this->tensors()[basename] = std::move(tensor);
133137
}
134138

@@ -138,11 +142,17 @@ class ImporterContext final : public IImporterContext
138142
if (layer)
139143
{
140144
const std::string name = basename.empty() ? layer->getName() : basename;
141-
const std::string uniqueName = generateUniqueName(mLayerNames, basename);
145+
const std::string uniqueName = generateUniqueName(mLayerNames, name);
142146

143147
auto* ctx = this; // To enable logging.
144-
LOG_VERBOSE("Registering layer: " << name << " for ONNX node: " << basename);
145-
148+
if (layer->getType() == nvinfer1::LayerType::kCONSTANT)
149+
{
150+
LOG_VERBOSE("Registering constant layer: " << uniqueName << " for ONNX initializer: " << basename);
151+
}
152+
else
153+
{
154+
LOG_VERBOSE("Registering layer: " << uniqueName << " for ONNX node: " << basename);
155+
}
146156
layer->setName(uniqueName.c_str());
147157
}
148158
}
@@ -228,7 +238,6 @@ class ImporterContext final : public IImporterContext
228238
return _opsets.at(domain);
229239
}
230240
}
231-
232241
private:
233242
std::string generateUniqueName(std::set<std::string>& namesSet, const std::string& basename)
234243
{

ModelImporter.cpp

Lines changed: 33 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -242,14 +242,16 @@ Status importInputs(ImporterContext* ctx, ::ONNX_NAMESPACE::GraphProto const& gr
242242
ASSERT(weight_desc.memoryType == ONNXIFI_MEMORY_TYPE_CPU, ErrorCode::kINVALID_VALUE);
243243
ASSERT(convertWeightDescriptor(weight_desc, &weights, ctx), ErrorCode::kUNSUPPORTED_NODE);
244244
tensor = weights;
245+
ctx->registerTensor(std::move(tensor), input.name());
245246
}
247+
// Do not register any initializers
246248
else if (!initializers.count(input.name()))
247249
{
248250
nvinfer1::ITensor* tensor_ptr;
249251
TRT_CHECK(importInput(ctx, input, &tensor_ptr));
250252
tensor = tensor_ptr;
253+
ctx->registerTensor(std::move(tensor), input.name());
251254
}
252-
ctx->registerTensor(std::move(tensor), input.name());
253255
}
254256

255257
return Status::success();
@@ -335,7 +337,6 @@ bool ModelImporter::supportsModel(
335337
}
336338
}
337339
auto* ctx = &_importer_ctx;
338-
339340
auto checkForInput = [&input_node, &ctx](::ONNX_NAMESPACE::NodeProto const& node) {
340341
for (auto input : node.input())
341342
{
@@ -347,7 +348,7 @@ bool ModelImporter::supportsModel(
347348
return false;
348349
};
349350

350-
auto checkForShapeTensors = [&ctx](::ONNX_NAMESPACE::NodeProto const& node){
351+
auto checkShapeTensorType = [&ctx](::ONNX_NAMESPACE::NodeProto const& node){
351352
for (int i = 0; i < ctx->network()->getNbInputs(); i++)
352353
{
353354
auto input = ctx->network()->getInput(i);
@@ -374,7 +375,7 @@ bool ModelImporter::supportsModel(
374375
std::vector<size_t> topological_order;
375376
if (!toposort(model.graph().node(), &topological_order))
376377
{
377-
LOG_ERROR("Failed to sort model topologically, exiting ...");
378+
cout << "Failed to sort model topologically, exiting ..." << endl;
378379
return false;
379380
}
380381

@@ -386,14 +387,13 @@ bool ModelImporter::supportsModel(
386387
// 2. It is not directly connected to an unsupported input
387388
// 3. It is not directly connected to an unsupported shape tensor input
388389
// 4. It did not illegally produce a shape tensor output
389-
// 5. It was sucessfully parsed
390+
// 5. The importer function did not throw an assertion
390391
bool registered = supportsOperator(node.op_type().c_str());
391-
bool containsInput = (input_node.empty()) ? false : checkForInput(node);
392-
bool containsShapeInput = checkForShapeTensors(node);
393-
auto tensorName = node.name();
394-
bool supportedShapeTensor = ctx->unsupportedShapeTensors().count(tensorName) == 0 ? true : false;
395-
bool containsIndex = node_idx == error_node;
396-
if (registered && !containsInput && !containsShapeInput && supportedShapeTensor && !containsIndex)
392+
bool unsupportedInput = (input_node.empty()) ? false : checkForInput(node);
393+
bool unsupportedShapeType = checkShapeTensorType(node);
394+
bool unsupportedShapeTensor = ctx->unsupportedShapeTensors().count(node.name()) > 0 ? true : false;
395+
bool unsuccessfulParse = node_idx == error_node;
396+
if (registered && !unsupportedInput && !unsupportedShapeType && !unsupportedShapeTensor && !unsuccessfulParse)
397397
{
398398
if (newSubGraph)
399399
{
@@ -408,7 +408,6 @@ bool ModelImporter::supportsModel(
408408
}
409409
else
410410
{
411-
LOG_WARNING("Found unsupported node: " << tensorName);
412411
// This is not a supported node, reset newSubGraph
413412
newSubGraph = true;
414413
allSupported = false;
@@ -468,10 +467,12 @@ void removeShapeTensorCasts(IImporterContext* ctx)
468467
nvinfer1::ILayer* layer = ctx->network()->getLayer(i);
469468
if (layer->getNbOutputs() > 0 && layer->getOutput(0)->isShapeTensor())
470469
{
470+
layer->resetPrecision();
471471
layer->resetOutputType(0);
472472
nvinfer1::ITensor& t = *layer->getOutput(0);
473473
// Assume that boolean tensors were not cast, and thus have their type correctly set.
474474
const nvinfer1::DataType shapeTensorType = t.getType() == nvinfer1::DataType::kBOOL ? nvinfer1::DataType::kBOOL : nvinfer1::DataType::kINT32;
475+
layer->setPrecision(shapeTensorType);
475476
layer->setOutputType(0, shapeTensorType);
476477
// Set type only if necessary, to avoid TensorRT warnings
477478
// about setting type of non-input/output tensors.
@@ -486,9 +487,9 @@ void removeShapeTensorCasts(IImporterContext* ctx)
486487
auto reduceOp = type == nvinfer1::LayerType::kREDUCE ? (static_cast<nvinfer1::IReduceLayer*>(layer))->getOperation() : nvinfer1::ReduceOperation::kSUM;
487488
if (!supportsShapeTensor(type, elementwiseOp, reduceOp))
488489
{
489-
auto name = layer->getName();
490+
auto name = layer->getOutput(0)->getName();
490491
ctx->unsupportedShapeTensors().insert(name);
491-
LOG_ERROR("Found unsupported shape-tensor producing layer:" << name);
492+
LOG_ERROR("Found " << name << " as a shape tensor output from a layer that does not support it!");
492493
}
493494
}
494495
}
@@ -526,14 +527,17 @@ Status ModelImporter::importModel(
526527
TRT_CHECK(importInputs(&_importer_ctx, graph, &_importer_ctx.tensors(), weight_count, weight_descriptors));
527528
TRT_CHECK(parseGraph(&_importer_ctx, graph, model.producer_name() == "TensorRT", &_current_node));
528529

530+
_current_node = -1;
529531
// Mark outputs defined in the ONNX model (unless tensors are user-requested)
530532
for (::ONNX_NAMESPACE::ValueInfoProto const& output : graph.output())
531533
{
532534
ASSERT(_importer_ctx.tensors().count(output.name()), ErrorCode::kINVALID_GRAPH);
533-
ASSERT(_importer_ctx.tensors().at(output.name()).is_tensor(), ErrorCode::kUNSUPPORTED_GRAPH);
534-
nvinfer1::ITensor* output_tensor_ptr = &_importer_ctx.tensors().at(output.name()).tensor();
535+
536+
nvinfer1::ITensor* output_tensor_ptr
537+
= &convertToTensor(_importer_ctx.tensors().at(output.name()), &_importer_ctx);
535538
LOG_VERBOSE("Marking " << output_tensor_ptr->getName() << " as output: " << output.name());
536539
output_tensor_ptr->setName(output.name().c_str());
540+
537541
if (output_tensor_ptr->isNetworkInput())
538542
{
539543
// HACK WAR for TRT not allowing input == output
@@ -543,6 +547,7 @@ Status ModelImporter::importModel(
543547
ASSERT(output_tensor_ptr, ErrorCode::kUNSUPPORTED_NODE);
544548
output_tensor_ptr->setName(output.name().c_str());
545549
}
550+
546551
nvinfer1::ITensor** user_output = _importer_ctx.getUserOutput(output.name().c_str());
547552
if (!user_output)
548553
{
@@ -640,24 +645,24 @@ Status ModelImporter::importModel(
640645
return Status::success();
641646
}
642647

643-
bool ModelImporter::parseFromFile(const char* onnxModelFile, int verbosity)
648+
bool ModelImporter::parseFromFile(const char* onnxModelFile, int32_t verbosity)
644649
{
645650
GOOGLE_PROTOBUF_VERIFY_VERSION;
646651
::ONNX_NAMESPACE::ModelProto onnx_model;
647652

648-
bool is_binary = ParseFromFile_WAR(&onnx_model, onnxModelFile);
653+
const bool is_binary = ParseFromFile_WAR(&onnx_model, onnxModelFile);
649654
if (!is_binary && !ParseFromTextFile(&onnx_model, onnxModelFile))
650655
{
651-
cerr << "Failed to parse ONNX model from file" << onnxModelFile << endl;
656+
cerr << "Failed to parse ONNX model from file: " << onnxModelFile << endl;
652657
return EXIT_FAILURE;
653658
}
654659

655660
// Keep track of the absolute path to the ONNX file.
656661
_importer_ctx.setOnnxFileLocation(onnxModelFile);
657662

658-
if (verbosity >= (int) nvinfer1::ILogger::Severity::kWARNING)
663+
if (verbosity >= static_cast<int32_t>(nvinfer1::ILogger::Severity::kWARNING))
659664
{
660-
int64_t opset_version = (onnx_model.opset_import().size() ? onnx_model.opset_import(0).version() : 0);
665+
const int64_t opset_version = (onnx_model.opset_import().size() ? onnx_model.opset_import(0).version() : 0);
661666
cout << "----------------------------------------------------------------" << endl;
662667
cout << "Input filename: " << onnxModelFile << endl;
663668
cout << "ONNX IR version: " << onnx_ir_version_string(onnx_model.ir_version()) << endl;
@@ -672,30 +677,30 @@ bool ModelImporter::parseFromFile(const char* onnxModelFile, int verbosity)
672677

673678
{ //...Read input file, parse it
674679
std::ifstream onnx_file(onnxModelFile, std::ios::binary | std::ios::ate);
675-
std::streamsize file_size = onnx_file.tellg();
680+
const std::streamsize file_size = onnx_file.tellg();
676681
onnx_file.seekg(0, std::ios::beg);
677682
std::vector<char> onnx_buf(file_size);
678683
if (!onnx_file.read(onnx_buf.data(), onnx_buf.size()))
679684
{
680-
cerr << "ERROR: Failed to read from file " << onnxModelFile << endl;
685+
cerr << "ERROR: Failed to read from file: " << onnxModelFile << endl;
681686
return false;
682687
}
683688
if (!parse(onnx_buf.data(), onnx_buf.size()))
684689
{
685-
int nerror = getNbErrors();
686-
for (int i = 0; i < nerror; ++i)
690+
const int32_t nerror = getNbErrors();
691+
for (int32_t i = 0; i < nerror; ++i)
687692
{
688693
nvonnxparser::IParserError const* error = getError(i);
689694
if (error->node() != -1)
690695
{
691696
::ONNX_NAMESPACE::NodeProto const& node = onnx_model.graph().node(error->node());
692697
cerr << "While parsing node number " << error->node() << " [" << node.op_type();
693-
if (node.output().size() && verbosity >= (int) nvinfer1::ILogger::Severity::kVERBOSE)
698+
if (node.output().size() && verbosity >= static_cast<int32_t>(nvinfer1::ILogger::Severity::kVERBOSE))
694699
{
695700
cerr << " -> \"" << node.output(0) << "\"";
696701
}
697702
cerr << "]:" << endl;
698-
if (verbosity >= (int) nvinfer1::ILogger::Severity::kVERBOSE)
703+
if (verbosity >= static_cast<int32_t>(nvinfer1::ILogger::Severity::kVERBOSE))
699704
{
700705
cout << "--- Begin node ---" << endl;
701706
cout << node << endl;
@@ -708,7 +713,7 @@ bool ModelImporter::parseFromFile(const char* onnxModelFile, int verbosity)
708713
return false;
709714
}
710715

711-
if (verbosity >= (int) nvinfer1::ILogger::Severity::kVERBOSE)
716+
if (verbosity >= static_cast<int32_t>(nvinfer1::ILogger::Severity::kVERBOSE))
712717
{
713718
cout << " ----- Parsing of ONNX model " << onnxModelFile << " is Done ---- " << endl;
714719
}

0 commit comments

Comments
 (0)