@@ -8,9 +8,117 @@ namespace converters {
8
8
namespace impl {
9
9
namespace {
10
10
11
+ bool MaxPoolingConverter (ConversionCtx* ctx, const torch::jit::Node* n, args& args) {
12
+ auto in = args[0 ].ITensor ();
13
+ auto shape = util::toVec (in->getDimensions ());
14
+
15
+ // Max Pool needs at least 4D input
16
+ if (shape.size () < 4 ) {
17
+ auto new_shape = util::toDimsPad (shape, 4 );
18
+ LOG_DEBUG (" Input shape is less than 4D got: " << util::toDims (shape) << " , inserting shuffle layer to reshape to 4D tensor shape: " << new_shape);
19
+ auto shuffle = ctx->net ->addShuffle (*in);
20
+ shuffle->setReshapeDimensions (new_shape);
21
+ shuffle->setName ((util::node_info (n) + " [Reshape to " + util::toStr (new_shape) + ' ]' ).c_str ());
22
+ in = shuffle->getOutput (0 );
23
+ }
24
+
25
+
26
+ auto kernel_size = util::toDims (args[1 ].unwrapToIntList ());
27
+ LOG_DEBUG (" kernel_size: " << kernel_size);
28
+ auto padding = util::toDims (args[3 ].unwrapToIntList ());
29
+ LOG_DEBUG (" padding: " << padding);
30
+ auto stride = util::toDims (args[2 ].unwrapToIntList ());
31
+ LOG_DEBUG (" stride: " << stride);
32
+
33
+ auto dilation = util::toDims (args[4 ].unwrapToIntList ());
34
+
35
+ TRTORCH_ASSERT (dilation == util::toDims (std::vector<int64_t >(dilation.nbDims , 1 )), " Pooling dilation is not supported in TensorRT" );
36
+
37
+ LOG_DEBUG (" dilation: " << dilation);
38
+ LOG_WARNING (" Dilation not used in max pooling converter" );
39
+ bool ceil_mode = args[5 ].unwrapToBool ();
40
+
41
+ auto new_layer = ctx->net ->addPoolingNd (*in, nvinfer1::PoolingType::kMAX , kernel_size);
42
+ TRTORCH_CHECK (new_layer, " Unable to create Max Pooling layer from node: " << *n);
43
+
44
+ new_layer->setName (util::node_info (n).c_str ());
45
+ new_layer->setPaddingNd (padding);
46
+ if (stride.nbDims != 2 && ctx->settings .device == nvinfer1::DeviceType::kDLA ) {
47
+ if (!ctx->settings .allow_gpu_fallback ) {
48
+ TRTORCH_THROW_ERROR (" DLA Pooling stride is limited to 2D, allow GPU fallback" );
49
+ } else {
50
+ LOG_WARNING (" DLA Pooling stride is limited to 2D, will run on GPU" );
51
+ }
52
+ }
53
+ new_layer->setStrideNd (stride);
54
+
55
+ auto padding_mode = ceil_mode ? nvinfer1::PaddingMode::kEXPLICIT_ROUND_UP : nvinfer1::PaddingMode::kEXPLICIT_ROUND_DOWN ;
56
+ new_layer->setPaddingMode (padding_mode);
57
+
58
+ new_layer->setName (util::node_info (n).c_str ());
59
+ auto out_tensor = ctx->AssociateValueAndTensor (n->outputs ()[0 ], new_layer->getOutput (0 ));
60
+
61
+ LOG_DEBUG (" Output tensor shape: " << out_tensor->getDimensions ());
62
+ return true ;
63
+ }
64
+
65
+ bool AvgPoolingConverter (ConversionCtx* ctx, const torch::jit::Node* n, args& args) {
66
+ auto in = args[0 ].ITensor ();
67
+ auto shape = util::toVec (in->getDimensions ());
68
+
69
+ // Avg Pool needs at least 4D input
70
+ if (shape.size () < 4 ) {
71
+ auto new_shape = util::toDimsPad (shape, 4 );
72
+ LOG_DEBUG (" Input shape is less than 4D got: " << util::toDims (shape) << " , inserting shuffle layer to reshape to 4D tensor shape: " << new_shape);
73
+ auto shuffle = ctx->net ->addShuffle (*in);
74
+ shuffle->setReshapeDimensions (new_shape);
75
+ shuffle->setName ((util::node_info (n) + " [Reshape to " + util::toStr (new_shape) + ' ]' ).c_str ());
76
+ in = shuffle->getOutput (0 );
77
+ }
78
+
79
+
80
+ auto kernel_size = util::toDims (args[1 ].unwrapToIntList ());
81
+ LOG_DEBUG (" kernel_size: " << kernel_size);
82
+ auto padding = util::toDims (args[3 ].unwrapToIntList ());
83
+ LOG_DEBUG (" padding: " << padding);
84
+ auto stride = util::toDims (args[2 ].unwrapToIntList ());
85
+ LOG_DEBUG (" stride: " << stride);
86
+
87
+ bool ceil_mode = args[4 ].unwrapToBool ();
88
+ bool count_inlcude_pad = args[5 ].unwrapToBool ();
89
+
90
+ auto new_layer = ctx->net ->addPoolingNd (*in, nvinfer1::PoolingType::kAVERAGE , kernel_size);
91
+ TRTORCH_CHECK (new_layer, " Unable to create Avg Pooling layer from node: " << *n);
92
+
93
+ new_layer->setName (util::node_info (n).c_str ());
94
+ new_layer->setPaddingNd (padding);
95
+ if (stride.nbDims != 2 && ctx->settings .device == nvinfer1::DeviceType::kDLA ) {
96
+ if (!ctx->settings .allow_gpu_fallback ) {
97
+ TRTORCH_THROW_ERROR (" DLA Pooling stride is limited to 2D, allow GPU fallback" );
98
+ } else {
99
+ LOG_WARNING (" DLA Pooling stride is limited to 2D, will run on GPU" );
100
+ }
101
+ }
102
+ new_layer->setStrideNd (stride);
103
+
104
+ auto padding_mode = ceil_mode ? nvinfer1::PaddingMode::kEXPLICIT_ROUND_UP : nvinfer1::PaddingMode::kEXPLICIT_ROUND_DOWN ;
105
+ new_layer->setPaddingMode (padding_mode);
106
+ new_layer->setAverageCountExcludesPadding (!count_inlcude_pad);
107
+
108
+ if (!(args[6 ].IValue ()->isNone ())) {
109
+ LOG_WARNING (" Divisor override is now handled by Avg Pooling Converter" );
110
+ }
111
+
112
+ new_layer->setName (util::node_info (n).c_str ());
113
+ auto out_tensor = ctx->AssociateValueAndTensor (n->outputs ()[0 ], new_layer->getOutput (0 ));
114
+
115
+ LOG_DEBUG (" Output tensor shape: " << out_tensor->getDimensions ());
116
+ return true ;
117
+ }
118
+
11
119
auto pooling_registrations TRTORCH_UNUSED = RegisterNodeConversionPatterns()
12
120
.pattern({
13
- " aten::max_pool2d (Tensor self, int[2 ] kernel_size, int[2 ] stride=[], int[2 ] padding=[0, 0 ], int[2 ] dilation=[1, 1 ], bool ceil_mode=False) -> (Tensor)" ,
121
+ " aten::max_pool1d (Tensor self, int[1 ] kernel_size, int[1 ] stride=[], int[1 ] padding=[], int[1 ] dilation=[], bool ceil_mode=False) -> (Tensor)" ,
14
122
[](ConversionCtx* ctx, const torch::jit::Node* n, args& args) -> bool {
15
123
auto in = args[0 ].ITensor ();
16
124
auto shape = util::toVec (in->getDimensions ());
@@ -25,38 +133,130 @@ auto pooling_registrations TRTORCH_UNUSED = RegisterNodeConversionPatterns()
25
133
in = shuffle->getOutput (0 );
26
134
}
27
135
28
-
29
- auto kernel_size = util::toDimsHW (args[1 ].unwrapToIntList ());
136
+ auto kernel_vec = args[1 ].unwrapToIntList ().vec ();
137
+ kernel_vec.insert (kernel_vec.begin (), 1 );
138
+ auto kernel_size = util::toDims (kernel_vec);
30
139
LOG_DEBUG (" kernel_size: " << kernel_size);
31
- auto padding = util::toDimsHW (args[3 ].unwrapToIntList ());
140
+ auto stride_vec = args[2 ].unwrapToIntList ().vec ();
141
+ stride_vec.insert (stride_vec.begin (), 1 );
142
+ auto stride = util::toDims (stride_vec);
143
+ LOG_DEBUG (" stride: " << stride);
144
+ auto padding_vec = args[3 ].unwrapToIntList ().vec ();
145
+ padding_vec.insert (padding_vec.begin (), 0 );
146
+ auto padding = util::toDims (padding_vec);
32
147
LOG_DEBUG (" padding: " << padding);
148
+
33
149
auto dilation = util::toDims (args[4 ].unwrapToIntList ());
34
150
35
- TRTORCH_ASSERT (dilation == util::toDims (std::vector<int64_t >({ 1 , 1 } )), " Pooling dilation is not supported in TensorRT" );
151
+ TRTORCH_ASSERT (dilation == util::toDims (std::vector<int64_t >(dilation. nbDims , 1 )), " Pooling dilation is not supported in TensorRT" );
36
152
37
153
LOG_DEBUG (" dilation: " << dilation);
38
154
LOG_WARNING (" Dilation not used in max pooling converter" );
39
- bool ceil_mode = args[5 ].IValue ()-> to < bool > ();
155
+ bool ceil_mode = args[5 ].unwrapToBool ();
40
156
41
157
auto new_layer = ctx->net ->addPoolingNd (*in, nvinfer1::PoolingType::kMAX , kernel_size);
42
- TRTORCH_CHECK (new_layer, " Unable to create Max Pool 2D layer from node: " << *n);
158
+ TRTORCH_CHECK (new_layer, " Unable to create Max Pooling layer from node: " << *n);
159
+
160
+ new_layer->setName (util::node_info (n).c_str ());
161
+ new_layer->setPaddingNd (padding);
162
+ if (stride.nbDims != 2 && ctx->settings .device == nvinfer1::DeviceType::kDLA ) {
163
+ if (!ctx->settings .allow_gpu_fallback ) {
164
+ TRTORCH_THROW_ERROR (" DLA Pooling stride is limited to 2D, allow GPU fallback" );
165
+ } else {
166
+ LOG_WARNING (" DLA Pooling stride is limited to 2D, will run on GPU" );
167
+ }
168
+ }
169
+ new_layer->setStrideNd (stride);
170
+
171
+ auto padding_mode = ceil_mode ? nvinfer1::PaddingMode::kEXPLICIT_ROUND_UP : nvinfer1::PaddingMode::kEXPLICIT_ROUND_DOWN ;
172
+ new_layer->setPaddingMode (padding_mode);
173
+
174
+ new_layer->setName (util::node_info (n).c_str ());
175
+ auto out_tensor = ctx->AssociateValueAndTensor (n->outputs ()[0 ], new_layer->getOutput (0 ));
176
+
177
+ LOG_DEBUG (" Output tensor shape: " << out_tensor->getDimensions ());
178
+ return true ;
179
+ }
180
+ }).pattern({
181
+ " aten::avg_pool1d(Tensor self, int[1] kernel_size, int[1] stride=[], int[1] padding=0, bool ceil_mode=False, bool count_include_pad=True) -> Tensor" ,
182
+ [](ConversionCtx* ctx, const torch::jit::Node* n, args& args) -> bool {
183
+ auto in = args[0 ].ITensor ();
184
+ auto shape = util::toVec (in->getDimensions ());
185
+
186
+ // Avg Pool needs at least 4D input
187
+ if (shape.size () < 4 ) {
188
+ auto new_shape = util::toDimsPad (shape, 4 );
189
+ LOG_DEBUG (" Input shape is less than 4D got: " << util::toDims (shape) << " , inserting shuffle layer to reshape to 4D tensor shape: " << new_shape);
190
+ auto shuffle = ctx->net ->addShuffle (*in);
191
+ shuffle->setReshapeDimensions (new_shape);
192
+ shuffle->setName ((util::node_info (n) + " [Reshape to " + util::toStr (new_shape) + ' ]' ).c_str ());
193
+ in = shuffle->getOutput (0 );
194
+ }
195
+
196
+
197
+ auto kernel_vec = args[1 ].unwrapToIntList ().vec ();
198
+ kernel_vec.insert (kernel_vec.begin (), 1 );
199
+ auto kernel_size = util::toDims (kernel_vec);
200
+ LOG_DEBUG (" kernel_size: " << kernel_size);
201
+ auto stride_vec = args[2 ].unwrapToIntList ().vec ();
202
+ stride_vec.insert (stride_vec.begin (), 1 );
203
+ auto stride = util::toDims (stride_vec);
204
+ LOG_DEBUG (" stride: " << stride);
205
+ auto padding_vec = args[3 ].unwrapToIntList ().vec ();
206
+ padding_vec.insert (padding_vec.begin (), 0 );
207
+ auto padding = util::toDims (padding_vec);
208
+ LOG_DEBUG (" padding: " << padding);
209
+
210
+ bool ceil_mode = args[4 ].unwrapToBool ();
211
+ bool count_inlcude_pad = args[5 ].unwrapToBool ();
212
+
213
+ auto new_layer = ctx->net ->addPoolingNd (*in, nvinfer1::PoolingType::kAVERAGE , kernel_size);
214
+ TRTORCH_CHECK (new_layer, " Unable to create Avg Pool 2D layer from node: " << *n);
43
215
44
216
new_layer->setName (util::node_info (n).c_str ());
45
217
new_layer->setPaddingNd (padding);
46
- if (args[2 ].unwrapToIntList ().size () == 2 ) {
47
- auto stride = util::toDims (args[2 ].unwrapToIntList ());
48
- new_layer->setStrideNd (stride);
218
+
219
+ if (stride.nbDims != 2 && ctx->settings .device == nvinfer1::DeviceType::kDLA ) {
220
+ if (!ctx->settings .allow_gpu_fallback ) {
221
+ TRTORCH_THROW_ERROR (" DLA Pooling stride is limited to 2D, allow GPU fallback" );
222
+ } else {
223
+ LOG_WARNING (" DLA Pooling stride is limited to 2D, will run on GPU" );
224
+ }
49
225
}
50
226
227
+ new_layer->setStrideNd (stride);
228
+
51
229
auto padding_mode = ceil_mode ? nvinfer1::PaddingMode::kEXPLICIT_ROUND_UP : nvinfer1::PaddingMode::kEXPLICIT_ROUND_DOWN ;
52
230
new_layer->setPaddingMode (padding_mode);
231
+ new_layer->setAverageCountExcludesPadding (!count_inlcude_pad);
53
232
54
233
new_layer->setName (util::node_info (n).c_str ());
55
234
auto out_tensor = ctx->AssociateValueAndTensor (n->outputs ()[0 ], new_layer->getOutput (0 ));
56
235
57
236
LOG_DEBUG (" Output tensor shape: " << out_tensor->getDimensions ());
58
237
return true ;
59
238
}
239
+ })
240
+ .pattern({
241
+ " aten::max_pool2d(Tensor self, int[2] kernel_size, int[2] stride=[], int[2] padding=[0, 0], int[2] dilation=[1, 1], bool ceil_mode=False) -> (Tensor)" ,
242
+ [](ConversionCtx* ctx, const torch::jit::Node* n, args& args) -> bool {
243
+ return MaxPoolingConverter (ctx, n, args);
244
+ }
245
+ }).pattern({
246
+ " aten::avg_pool2d(Tensor self, int[2] kernel_size, int[2] stride=[], int[2] padding=[0, 0], bool ceil_mode=False, bool count_include_pad=True, int? divisor_override=None) -> (Tensor)" ,
247
+ [](ConversionCtx* ctx, const torch::jit::Node* n, args& args) -> bool {
248
+ return AvgPoolingConverter (ctx, n, args);
249
+ }
250
+ }).pattern({
251
+ " aten::max_pool3d(Tensor self, int[3] kernel_size, int[3] stride=[], int[3] padding=[], int[3] dilation=[], bool ceil_mode=False) -> (Tensor)" ,
252
+ [](ConversionCtx* ctx, const torch::jit::Node* n, args& args) -> bool {
253
+ return MaxPoolingConverter (ctx, n, args);
254
+ }
255
+ }).pattern({
256
+ " aten::avg_pool3d(Tensor self, int[3] kernel_size, int[3] stride=[], int[3] padding=[], bool ceil_mode=False, bool count_include_pad=True, int? divisor_override=None) -> (Tensor)" ,
257
+ [](ConversionCtx* ctx, const torch::jit::Node* n, args& args) -> bool {
258
+ return AvgPoolingConverter (ctx, n, args);
259
+ }
60
260
}).pattern({
61
261
" aten::adaptive_avg_pool2d(Tensor self, int[2] output_size) -> (Tensor)" ,
62
262
[](ConversionCtx* ctx, const torch::jit::Node* n, args& args) -> bool {
0 commit comments