阅前须知Ⅰ. IPU SDK 支持
1. Caffe支持算子¶
| 算子 | 备注 |
|---|---|
| ArgMax | only support top 1 |
| Axpy | |
| BatchNorm | |
| Concat | 最大1024个tensor concat |
| Convolution | 限制条件:All tensor size < 2^31 若kernel size 为 do*h*w*di 则h * w < 64 group为1时:转换成Depthwise Convolution; group为C时:转换为Convolution; group为 (1, C) 时:拆解成GroupConv round(di/16)*round(do/16) < 512 * 1024 |
| ConvolutionDepthwise | 原生支持Kernel_size为3*3,6*6,9*9,其余情况转换成Convolution处理限制条件:Pad范围:[0, 1] |
| CReLU | 输入<=4维 |
| ContinuationIndicator | |
| Crop | |
| Deconvolution | All tensor size < 2^31 若kernel size 为 do*h*w*di,h * w < 64 round(di/16)*round(do/16) < 512 * 1024 |
| Dropout | |
| Eltwise | 其中PROD和SUM,对于输入的两个tensor,当为4维向量时,满足下面条件 1. NCHW ,const 2. NCHW ,C维向量 3. NCHW ,NCHW 当为5维向量时,满足 1. NCDHW ,const 2. NCDHW ,NCDHW |
| Flatten | |
| InnerProduct | 若weight size do*di round(di/16)*round(do/16) < 512 * 1024 |
| Permute | |
| Pooling | 若kernel size为h*w 1.AVGPooling (1).FilterW <= 255,FilterH <= 255, (2).AvePooling_U8:FilterMax(FilterW*FilterH) = 12288, (3).AvePooling_S16:FilterMax(FilterW*FilterH) = 12288 2.MaxPooling: 需FilterW <= 255,且FilterMax(FilterW*FilterH) = 6029312 |
| PriorBox | |
| Power | 仅支持指数为正整数 |
| Reshape | |
| Reverse | |
| ROIPooling | ROIPooling的rois输入维度为(N×5),当后段网络全部是InnerProduct时,N才可以设置大于1,如果后段网络中有卷积时,N仅可以设置为1,第二段网络需要循环执行N次。使用方法和限制详见下方Please Note。 |
| ReLU | 输入<=4维 |
| PRuLU | 输入<=4维 |
| Sigmoid | |
| Slice | |
| Scale | 对于输入的两个tensor,shape满足下面条件 1. 4维向量,NCHW 2. NCHW ,const 3. NCHW ,C维向量 4. NCHW ,NCHW 当为5维向量时,满足 1. NCDHW ,const 2. NCDHW ,NCDHW |
| Softmax | 如需对指定维度进行运算,将要计算的维度转置到最后的维度(最内维度),最大支持32*512=16384 |
| Splite | |
| ShuffleChannel | |
| Tanh | 输入<=4维 |
| Threshold | 只支持4维输入 |
| Tile | |
| Upsample | Upsample算子在caffe中没有,可以手动将Deconvolution修改成Upsample 只支持4维输入 Only support same scale on H and W |
| Reorg | 只支持stride = 2 |
| LSTM | 支持单向,双向 |
Please Note:
-
Upsample算子在prototxt中这样描述:
scale参数与Deconvolution的Stride含义相同。但需注意Upsample相当于权重全为1的Deconvolution算子。layer { bottom: "layer85-conv" top: "layer86-upsample" name: "layer86-upsample" type: "Upsample" upsample_param { scale: 2 } } -
ROIPooling算子在prototxt中这样描述:
Roi_pooling_param仅支持pooled_w,pooled_h和spatial_scale。Float模型的rois输入为rpn层输出的坐标,Fixed和Offline模型的rois输入为rpn层输出坐标乘spatial_scale值后再量化到int16后送入模型。layer { name: "roi_pool5" type: "ROIPooling" bottom: "conv5_3" bottom: "rois" top: "pool5" roi_pooling_param { pooled_w: 7 pooled_h: 7 spatial_scale: 0.0625 } }
2. TensorFlow支持算子¶
| 算子 | 备注 |
|---|---|
| Convolution | 限制条件:Kernel_size:H * W < 64 |
| DepthwiseConv2dNative | 原生支持Kernel_size为3*3,6*6,9*9,其余情况转换成Convolution处理 |
| FullyConnected | |
| Max pooling | |
| Average Pooling | |
| ReLU | |
| PReLU | |
| ReLU6 | |
| LeakyReLU | |
| Sigmoid | |
| Less | |
| Log | |
| Greater | |
| GreaterEqual | |
| Equal | |
| Add | |
| Sub | |
| Mul | |
| RealDiv | 仅支持第二个操作数为常量Tensor |
| FloorDiv | 仅支持第二个操作数为常量Tensor |
| Maximum | |
| Minimum | |
| Mean | |
| Max | |
| Sqrt | |
| Sin | |
| Cos | |
| Rsqrt | |
| Round | |
| Softmax | 如需对指定维度进行运算,将要计算的维度转置到最后的维度(最内维度) |
| FusedBatchNorm | |
| Exp | |
| Align | |
| ConcatV2 | |
| Fill | |
| Gather | 仅支持第二个操作数indices为常量Tensor |
| GatherV2 | |
| Pack | |
| Pad | |
| SpaceToBatchND | |
| BatchToSpaceND | |
| Zeroslike | |
| Split | |
| Slice | |
| Unpack | |
| Tile | |
| Reshape | |
| Transpose | |
| Resize_bilinear | |
| Resize_NearestNeighbor | |
| Batch_matmul | |
| TopKV2 | |
| Tanh | |
| Concatenation | |
| Argmax | |
| Logistic | |
| TransposeConv | |
| Square | |
| StrideSlice | |
| Abs | |
| Sum | |
| Cast |
3. Onnx支持算子¶
| 算子 | 备注 |
|---|---|
| Abs | 无限制 |
| Add | 无限制 |
| And | 无限制 |
| ArgMax | axis:无限制 keepdims:无限制 select_last_index:只能被设置为0 |
| ArgMin | axis: 无限制 keepdims:无限制 select_last_index:只能被设置为0 |
| Atan | 无限制 |
| AveragePool | auto_pad:支持,SAME_UPPER, SAME_LOWER or VALID ceil_mode:仅支持0 kernel_shape: 若kernel_shape为h*w,需满足FilterW <= 255,FilterH <= 255 pads:支持两个维度,都是[0,255] strides:支持两个维度,都是[0,255] count_include_pad:无限制 dilation:只支持为1 |
| BatchNormalization | epsilon: 无限制 momentum: 不支持 training_mode: 不支持 is_test:不支持 spatial:不支持 |
| Cast | to: 支持float32/float64/int64/int32/bool saturate:不支持 |
| Clip | 无限制 |
| Concat | 1和Q版本最大支持256个tensor concat,其余版本最大支持10000 |
| Constant | value:支持,其余属性不支持 |
| Conv | conv1d: All tensor size < 2^31 auto_pad: 支持,SAME_UPPER, SAME_LOWER or VALID dilations:无限制 group:小于等于C kernel_shape:支持,h * w < 64 pads:支持,四个维度,都是[0,15] strides:支持,两个维度,都是[0, 31] conv2d: All tensor size < 2^31 auto_pad: 支持,SAME_UPPER, SAME_LOWER or VALID dilations:无限制 group:小于等于C kernel_shape:支持,h * w < 64 pads:支持,四个维度,都是[0,15] strides:支持,两个维度,都是[0, 31] conv3d: All tensor size < 2^31 auto_pad: 支持,SAME_UPPER, SAME_LOWER or VALID dilations:无限制 group:不支持 kernel_shape:支持,h * w < 255,d维无限制 pads:支持h,w,d三个维度六个方向,都是[0, 15] strides:支持h,w两个维度,都是[0, 31],d维只支持1 |
| ConvTranspose | All tensor size < 2^31 auto_pad: 支持,SAME_UPPER, SAME_LOWER or VALID dilations:只支持为 1 group:只支持1或者C kernel_shape:支持,h * w < 255 output_padding:支持 output_shape:不支持 pads:支持,四个维度,都是[0,15], 每个维度pad值需相等 strides:支持,两个维度,都是[0, 31] |
| Cos | 无限制 |
| CumSum | exclusive:只支持设置为0 reverse:只支持设置为0 |
| DepthToSpace | blocksize:支持,各个维度可以整除blocksize mode:DCR or CRD |
| Div | 无限制 |
| Dropout | is_test:不支持 ratio:不支持 seed:不支持 |
| Einsum | equation:无限制 支持单双操作数,不支持省略维度格式的表达式 |
| Elu | alpha:无限制 |
| Equal | 无限制 |
| Erf | 无限制 |
| Exp | 无限制 |
| Expand | 无限制 |
| Flatten | axis:无限制 |
| Floor | 无限制 |
| GRU | activation_alpha:不支持 activation_beta:不支持 activations:只支持sigmoid/tanh clip:不支持 direction:支持forward和bidirectional layout:只支持为0 linear_before_offset:支持0和1 |
| Gather | axis:无限制<br s6不知第二个输入是variable tensor |
| GatherElements | axis:无限制 |
| Gelu | approximate:只支持为None |
| Gemm | alpha:无限制 beta:无限制 transA:无限制 transB:无限制 |
| GlobalAveragePool | kernel_shape: 若kernel_shape为h*w,需满足FilterW <= 255,FilterH <= 255 pads:支持两个维度,都是[0,255] strides:支持两个维度,都是[0,255] |
| GlobalMaxPool | kernel_shape: 若kernel_shape为h*w,需满足FilterW <= 255,FilterH <= 255 pads:支持两个维度,都是[0,255] strides:支持两个维度,都是[0,255] |
| Greater | 无限制 |
| GreaterOrEqual | 无限制 |
| HardSigmoid | alpha:无限制 beta:无限制 |
| Identity | 此算子在转换过程中会被移除掉 |
| InstanceNormalization | epsilon:无限制 |
| LSTM | activation_alpha:不支持 activation_beta:不支持 activations:只支持sigmoid/tanh clip:不支持 direction:只支持forward和bidirectional input_forget:只支持为0 layout:只支持为0 |
| LayerNormal | axis:不支持0 epsilon:无限制 stash_type:不支持 |
| LayerNormalization | axis:不支持0 epsilon:无限制 stash_type:不支持 |
| LeakyRelu | alpha:无限制 输入<=4维 |
| Less | 无限制 |
| Log | 无限制 |
| LogSoftmax | 无限制 |
| MatMul | 无限制 |
| Max | 无限制 |
| MaxPool | auto_pad:支持,SAME_UPPER, SAME_LOWER or VALID ceil_mode:仅支持0 kernel_shape:支持 pads:支持 strides:支持 storage_order:不支持 若kernel size为h*w,需满足 FilterW <= 255,FilterH <= 255 |
| MeanVarianceNormalization | 输入只支持四维 axes:无限制 |
| Min | 无限制 |
| Mul | 无限制 |
| Neg | 无限制 |
| Not | 无限制 |
| PRelu | 无限制 |
| Pad | mode:支持constant/reflect value:无限制 不支持axes作为输入 |
| Pow | 无限制 |
| Reciprocal | 无限制 |
| ReduceL2 | axes:无限制 keepdims:无限制 noop_with_empty_axes:只支持为0 |
| ReduceMax | axes:无限制 keepdims:无限制 noop_with_empty_axes:只支持为0 |
| ReduceMean | axes:无限制 keepdims:无限制 noop_with_empty_axes:只支持为0 |
| ReduceMin | axes:无限制 keepdims:无限制 noop_with_empty_axes:只支持为0 |
| ReduceSum | axes:无限制 keepdims:无限制 noop_with_empty_axes:只支持为0 |
| Relu | 无限制 |
| Reshape | allowzero:只支持为0,不支持output shape里面有0值 |
| Resize | 只支持对hw做resize antialias:只支持为0 axes:无限制 coordinate_transformation_mode:支持align_corners/asymmetric/half_pixel/pytorch_half_pixel,SDK版本S6和S2不支持half_pixel和pytorch_half_pixel mode:支持nearest或者linear cubic_coeff_a:不支持 exclude_outside:只支持为0 extrapolation_value:不支持 keep_aspect_ratio_policy:不支持 nearest_mode:支持,[round_prefer_floor,floor,round_prefer_ceil] |
| Round | 无限制 |
| ScatterElements | reduction:只支持为None axis:无限制 |
| ScatterND | reduction:只支持为None |
| Shape | end:无限制 start:无限制 |
| Sigmoid | 无限制 |
| Sin | 无限制 |
| Slice | axes:无限制 ends:无限制 starts:无限制 |
| Softmax | axis:无限制 |
| Softplus | 无限制 |
| SpaceToDepth | blocksize:无限制 |
| Split | axis:无限制 split:1和Q版本最大支持256,其余版本最大支持10000 num_outputs:不支持 |
| Sqrt | 无限制 |
| Squeeze | axes:无限制 |
| Sub | 无限制 |
| Sum | 只支持两个输入 |
| Tanh | 无限制 |
| Tile | 无限制 |
| TopK | axis:无限制 largest:只支持为1 sorted:无限制 k:无限制 |
| Transpose | perm:无限制 |
| Unsqueeze | 无限制 |
| Upsample | 只支持在HW维度上做Upsample,并且scale要相同 mode:支持nearest和linear height_scale:无限制 width_scale:无限制 scales:无限制 |
| Where | 无限制 |
4. SigmaStar IPU SDK对模型的限制¶
对于指定维度的Softmax,我们只支持对最内维度的操作(多余多维Tensor的Softmax运算,我们只支持Softmax制定在最内维度做)。
除第一层Conv外,其他层的Conv DI维度(即NHWC 中C这个维度)越大效率会越高,最大支援2048。
Math类算子(包括Add、Sub、Mul、Div等元素操作的算子),如果右操作数是scaler(单个数字) 或者 1 维向量(HW维度数据相同,C维度不同),效率会更高。
网络结构中尽量减少一个算子的输出被多个算子作为输入的情况,如ResNet的残差结构,GoogLeNet的Inception模块等。可参考构建BW友好型模型
5. 模型性能优化规则¶
(1)对于卷积的性能优化
kernel size 3x3 最好,特别对于首层。
kernel size 1x1 的时候,input tensor 最内维度shape值对齐到16 最好。
(2)对于DMA算子
concatenation算子比pack算子性能更好。
split比slice算子性能更好。
尽量减少在最内维上做transpose。
单口elementwise 算子的const 操作数最好是右操作数,即input[1]。
(3)综合部分
Tensor的维度为4最好。
Tensor最内维的shape值对齐到32最好。
Softmax最好只对最内维度操作。
ReduceMax、ReduceMin、ReduceSum最好坍塌的纬度是相邻的。
(4)模型结构优化
case1: Pad + Conv2D/DepthwiseConv
——conv或DepthwiseConv前的pad会被合并到卷积中,pad几乎不占用时间。
示例:

case2: Conv2D/DepthwiseConv + 单口elt
——conv后的单口elt会被合并,目前支持单口mul,单口add,单口div(会被转换成单口mul),且如果elt连续,则会被一起合并(见示例一和示例二),双口的elt则不会被合并(见示例三)。
示例一:

示例二:

示例三:

case3: Conv2D/DepthwiseConv + BatchNorm
——Mul和Add算子会和卷积一起运算。我们会把BatchNorm转换成Mul+Add, 所以可以合并。
case4: Pad + avgPooling
——pool前的pad会被合并,但是pool后的pad不会被合并 (globalpool会被转成对应的avg或max, 故也会与pad合并)
示例:

- case5: 连续的transpose会自动合并为一个。
示例:

case6: 连续的单口的相同elementwise算子会合并。
——elt的type需相同,输入可以不同
示例:

case7: 单独的单口mul和单口add,会变成MultAdd单一的算子。
——输入最内维需相等。
示例:

注意:这里单口意思为一个数据是constant的情况
case8: 模型中间的conv + 单口elt + relu
——只有模型中间层的结构会被合并,若连接了模型输出则不会被合并(但会进行内存优化,详见内存优化部分的说明)。
示例:

case9: 模型中间的conv + batchnorm + relu
参考case8。
示例:

case10: 模型中间的conv + relu
参考case8。
示例:

(5)模型内存优化
case1: Conv2D/DepthwiseConv2d + elementwise
——conv后的elt会被融合,融合指tensor共享一块memory,目前支持mul(单口、双口),add(单口、双口), div(单口,不支持双口),且环形elt也会参与融合
示例一:

示例二:

case2: Conv2D/DepthwiseConv2d + relu
——conv后的relu会被融合
示例:

case3: 结构优化结合内存优化
——如conv后的elt会被结构优化,而conv后的relu会被内存优化,见示例。
示例:

(6)构建BW友好的AI模型
BW友好的AI模型指模型数据尽可能不占用系统总线BW资源,BW计算公式如下:
BW = Input BW + Output BW + Const BW + Variable BW
其中,可以通过减少variable bw来提升模型性能,variable bw将受以下两点影响:
(1) tensor数据量太大
(2) tensor的生命周期太长
示例一:BW友好型

示例二:tensor的生命周期太长

示例三:tensor数据量太大

上图展示了三种常见的模型结构图,其中图一所示的结构符合模型优化规则,图二、图三所示的结构将影响模型性能。构建模型时请尽可能减少图二、图三结构的使用。