Exemple #1
0
def _create_conv2d_leaky_relu_nhwc_oihw(
    in_shape,
    w_shape,
    conv_padding,
    conv_strides,
    conv_dilation,
    kernel_layout="OIHW",
    target="DPUCZDX8G-zcu104",
) -> XGraph:

    kernel_w, kernel_h = w_shape[2], w_shape[3]
    W = np.random.randint(-10, 10, size=w_shape).astype(np.float32)
    # B = np.array([1., -1.], dtype=np.float32)

    x1 = px.ops.input("in1", shape=list(in_shape))
    w1 = px.ops.constant("weight", W)
    conv1 = px.ops.conv2d(
        op_name="conv1",
        input_layer=x1,
        weights_layer=w1,
        kernel_size=[kernel_w, kernel_h],
        strides=list(conv_strides),
        padding_hw=list(conv_padding),
        dilation=list(conv_dilation),
        data_layout="NHWC",
    )
    lr1 = px.ops.leaky_relu("lr1", [conv1], alpha=0.1)
    net = [x1, conv1, lr1]
    xgraph = XGRAPH_FACTORY.build_from_xlayer(net)
    xgraph = px.partition(xgraph, [target])
    return xgraph
Exemple #2
0
 def convert_pyxir(self, target):
     """Convert Relay expression to PyXIR XGraph"""
     xgraph = pyxir.frontend.tvm.from_relay(self.function,
                                            params=self.params,
                                            postprocessing=None)
     xgraph = pyxir.partition(xgraph, targets=[target])
     return xgraph
Exemple #3
0
def annotation(mod, params, target):
    """Annotate Relay expression for Vitis-AI DPU accelerators"""
    xgraph = pyxir.frontend.tvm.from_relay(mod, params, postprocessing=None)
    xgraph = pyxir.partition(xgraph, targets=[target])

    layers = xgraph.get_layers()
    relay_ids = [
        list(np.array(layer.attrs["relay_id"]).flatten()) for layer in layers
        if layer.target == target
    ]
    relay_ids_flatten = [item for sublist in relay_ids for item in sublist]
    mod = VitisAIAnnotationPass("vitis_ai", relay_ids_flatten)(mod)

    return mod
Exemple #4
0
def _create_conv2d_pool2d_nhwc_oihw(
    in_shape,
    w_shape,
    conv_padding,
    conv_strides,
    conv_dilation,
    pool_type,
    pool_size,
    pool_padding=[0, 0],
    pool_strides=[1, 1],
    conv_groups=1,
    conv_invalid=False,
    kernel_layout="OIHW",
    target="DPUCZDX8G-zcu104",
    conv_name="conv1",
    pool_name="pool1",
) -> XGraph:

    kernel_w, kernel_h = w_shape[2], w_shape[3]
    W = np.random.randint(-10, 10, size=w_shape).astype(np.float32)
    # B = np.array([1., -1.], dtype=np.float32)

    x1 = px.ops.input("in1", shape=list(in_shape))
    w1 = px.ops.constant("weight", W)
    conv1 = px.ops.conv2d(
        op_name=conv_name,
        input_layer=x1,
        weights_layer=w1,
        kernel_size=[kernel_w, kernel_h],
        strides=list(conv_strides),
        padding_hw=list(conv_padding),
        dilation=list(conv_dilation),
        groups=conv_groups,
        data_layout="NHWC",
    )
    pool1 = px.ops.pool2d(
        op_name=pool_name,
        input_layer=conv1,
        pool_type=pool_type,
        pool_size=list(pool_size),
        padding=list(pool_padding),
        layout="NHWC",
    )
    net = [x1, conv1, pool1]
    xgraph = XGRAPH_FACTORY.build_from_xlayer(net)
    xgraph = px.partition(xgraph, [target])
    return xgraph
Exemple #5
0
def annotation(mod, params, target):
    """Annotate Relay expression for Vitis-AI DPU accelerators"""
    # We need type information for supporting models that contain operations that don't
    #   have a Relay to XLayer translation
    mod = relay.transform.InferType()(mod)

    xgraph = pyxir.frontend.tvm.from_relay(mod, params, postprocessing=None)
    xgraph = pyxir.partition(xgraph, targets=[target])

    layers = xgraph.get_layers()
    relay_ids = [
        list(np.array(layer.attrs["relay_id"]).flatten()) for layer in layers
        if layer.target == target
    ]
    relay_ids_flatten = [item for sublist in relay_ids for item in sublist]
    mod = VitisAIAnnotationPass("vitis_ai", relay_ids_flatten)(mod)

    return mod
Exemple #6
0
    def test_basic(self):
        x1 = px.ops.input("in1", shape=[1, 1, 4, 4])
        x2 = px.ops.input("in2", shape=[1, 2, 2, 2])
        w1 = px.ops.constant("weight", np.ones((2, 1, 2, 2), dtype=np.float32))
        conv = px.ops.conv2d(
            op_name="conv1",
            input_layer=x1,
            weights_layer=w1,
            kernel_size=[2, 2],
            strides=[1, 1],
            padding_hw=[0, 0, 0, 0],
            dilation=[1, 1],
            groups=1,
            channels=2,
            data_layout="NCHW",
            kernel_layout="OIHW",
        )
        pool = px.ops.pool2d(
            op_name="pool1",
            input_layer=conv,
            pool_type="Avg",
            pool_size=[2, 2],
        )
        add = px.ops.eltwise("add1", pool, x2)
        net = [x1, x2, conv, pool, add]
        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 5
        assert p_xgraph.get_subgraph_names() == ["xp0"]

        p_xlayers = p_xgraph.get_layers()
        assert p_xlayers[0].type[0] in ["Input"]
        assert p_xlayers[1].type[0] in ["Convolution"]
        assert p_xlayers[2].type[0] in ["Pooling"]
        assert p_xlayers[3].type[0] in ["Input"]
        assert p_xlayers[4].type[0] in ["Eltwise"]

        assert p_xlayers[0].target == "cpu"
        assert p_xlayers[1].target == "test"
        assert p_xlayers[2].target == "test"
        assert p_xlayers[3].target == "cpu"
        assert p_xlayers[4].target == "test"

        assert p_xlayers[0].subgraph is None
        assert p_xlayers[1].subgraph == "xp0"
        assert p_xlayers[2].subgraph == "xp0"
        assert p_xlayers[3].subgraph is None
        assert p_xlayers[4].subgraph == "xp0"

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp0 = subgraphs[0]
        assert xp0.name == "xp0"
        xp0_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp0.subgraph_data)

        assert xp0.bottoms == ["in1", "in2"]
        assert xp0.tops == []
        assert xp0.shapes == [[-1, 2, 2, 2]]
        assert xp0.sizes == [8]

        assert len(xp0_xgraph) == 5
        xp0_layers = xp0_xgraph.get_layers()

        assert xp0_layers[0].type[0] == "Input"
        assert xp0_layers[0].layer[0] == "conv1"
        assert xp0_layers[1].type[0] == "Convolution"
        assert xp0_layers[2].type[0] == "Pooling"
        assert xp0_layers[3].type[0] == "Input"
        assert xp0_layers[4].type[0] == "Eltwise"

        assert xp0_layers[0].bottoms == []
        assert xp0_layers[0].tops == ["conv1"]
        assert xp0_layers[1].bottoms == ["xinput0"]
        assert xp0_layers[1].tops == ["pool1"]
        assert xp0_layers[2].bottoms == ["conv1"]
        assert xp0_layers[2].tops == ["add1"]
Exemple #7
0
    def test_inception_like_block(self):
        x1 = px.ops.input("in1", shape=[1, 1, 4, 4])
        x2 = px.ops.input("in2", shape=[1, 1, 4, 4])
        concat1 = px.ops.concat("concat1", [x1, x2], axis=1)  # 1, 2, 4, 4
        w1 = px.ops.constant("weight", np.ones((4, 2, 2, 2), dtype=np.float32))
        conv1 = px.ops.conv2d(
            op_name="conv1",
            input_layer=concat1,
            weights_layer=w1,
            kernel_size=[2, 2],
        )  # 1, 4, 3, 3
        pool1 = px.ops.pool2d(
            op_name="pool1",
            input_layer=conv1,
            pool_type="Avg",
            pool_size=[2, 2],
        )  # 1, 4, 2, 2
        w2 = px.ops.constant("weight2", np.ones((4, 2, 2, 2),
                                                dtype=np.float32))
        conv2 = px.ops.conv2d(
            op_name="conv2",
            input_layer=concat1,
            weights_layer=w2,
            kernel_size=[2, 2],
            strides=[2, 2],
        )  # 1, 4, 2, 2
        concat2 = px.ops.concat("concat2", [pool1, conv2],
                                axis=1)  # 1, 8, 2, 2
        net = [x1, x2, concat1, conv1, pool1, conv2, concat2]
        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 7
        p_xlayers = p_xgraph.get_layers()

        assert p_xlayers[0].target == "cpu"
        assert p_xlayers[1].target == "cpu"
        assert p_xlayers[2].target == "cpu"
        assert p_xlayers[3].target == "test"
        assert p_xlayers[4].target == "test"
        assert p_xlayers[5].target == "cpu"
        assert p_xlayers[6].target == "cpu"

        assert p_xlayers[0].subgraph is None
        assert p_xlayers[1].subgraph is None
        assert p_xlayers[2].subgraph is None
        assert p_xlayers[3].subgraph == "xp0"
        assert p_xlayers[4].subgraph == "xp0"
        assert p_xlayers[5].subgraph is None
        assert p_xlayers[6].subgraph is None

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp0 = subgraphs[0]
        assert xp0.name == "xp0"
        xp0_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp0.subgraph_data)

        assert xp0.bottoms == ["concat1"]
        assert xp0.tops == ["concat2"]
        assert xp0.shapes == [[-1, 4, 2, 2]]
        assert xp0.sizes == [16]

        assert len(xp0_xgraph) == 3
        xp0_layers = xp0_xgraph.get_layers()

        assert xp0_layers[0].type[0] == "Input"
        assert xp0_layers[1].type[0] == "Convolution"
        assert xp0_layers[2].type[0] == "Pooling"
Exemple #8
0
    def test_small(self):
        net = [
            XLayer(name='in1',
                   type=['Input'],
                   shapes=[1, 1, 4, 4],
                   sizes=[16],
                   bottoms=[],
                   tops=['conv1'],
                   layer=['in1'],
                   targets=[]),
            XLayer(name='in2',
                   type=['Input'],
                   shapes=[1, 2, 2, 2],
                   sizes=[8],
                   bottoms=[],
                   tops=['dense1'],
                   layer=['in2'],
                   targets=[]),
            XLayer(name='conv1',
                   type=['Convolution'],
                   shapes=[1, 2, 3, 3],
                   sizes=[18],
                   bottoms=['in1'],
                   tops=['pool1'],
                   layer=['conv1'],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]],
                       'kernel_size': [3, 3],
                       'strides': [1, 1],
                       'dilation': [1, 1],
                       'groups': 1,
                       'channels': [2, 2]
                   },
                   targets=[]),
            XLayer(name='pool1',
                   type=['Pooling'],
                   shapes=[1, 2, 2, 2],
                   sizes=[8],
                   bottoms=['conv1'],
                   tops=['dense1'],
                   layer=['pool1'],
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]],
                       'kernel_size': [3, 3],
                       'strides': [1, 1],
                   },
                   targets=[]),
            XLayer(name='dense1',
                   type=['Dense'],
                   shapes=[1, 20],
                   sizes=[20],
                   bottoms=['pool1', 'in2'],
                   tops=[],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   layer=['dense1'],
                   targets=[])
        ]
        xgraph = TestDPUContrib.xgraph_factory.build_from_xlayer(net)
        p_xgraph = partition(xgraph, ['dpuv2-zcu104'])
        dpu_xgraph = TestDPUContrib.target_registry\
            .get_target_build_func('dpuv2-zcu104')(p_xgraph)

        assert len(dpu_xgraph) == 6
        layers = dpu_xgraph.get_layers()

        assert layers[0].type[0] == 'Input'

        assert layers[1].type[0] == 'Transpose'
        assert layers[1].bottoms == ['in1']
        assert layers[1].tops == ['xp0']

        assert layers[2].type[0] == 'DPU'
        assert layers[2].bottoms == ['conv1_bottom_NCHW>NHWC']
        assert layers[2].tops == ['pool1']
        assert layers[2].shapes == [[1, 2, 2, 2]]
        assert layers[2].attrs['target'] == 'dpuv2-zcu104'
        assert layers[2].attrs['input_names'] == ['xinput0']
        assert layers[2].attrs['output_names'] == ['pool1']
        assert layers[2].attrs['input_layers']['xinput0'] == ['conv1']
        assert layers[2].attrs['output_layers']['pool1'] == ['pool1']
        assert layers[2].attrs['__top_tensors'] ==\
            {'pool1': ['pool1_top_NHWC>NCHW']}
        assert layers[2].attrs['orig_top_tensors'] ==\
            {'pool1': ['dense1']}
        assert layers[2].attrs['__bottom_tensors'] ==\
            {'xinput0': ['conv1_bottom_NCHW>NHWC']}
        assert layers[2].attrs['orig_bottom_tensors'] ==\
            {'xinput0': ['in1']}

        # Merged TupleGetItem and Transpose layer
        assert layers[3].type[0] == 'TupleGetItem'
        assert layers[3].name == 'pool1'
        assert layers[3].shapes == [1, 2, 2, 2]
        assert layers[3].bottoms == ['xp0']
        assert layers[3].tops == ['dense1']
        assert layers[3].attrs['transpose'] is True

        assert layers[4].type[0] == 'Input'
        assert layers[4].name == 'in2'
        assert layers[4].tops == ['dense1']

        assert layers[5].type[0] == 'Dense'
        assert layers[5].name == 'dense1'
        assert layers[5].shapes == [1, 20]
        assert layers[5].bottoms == ['pool1', 'in2']
        assert layers[5].tops == []
Exemple #9
0
    def test_xgraph_device_tagging(self):

        xgraph = XGraph()
        xgraph.add(XLayer(
            name='in1',
            type=['Input'],
            bottoms=[],
            tops=[],
            targets=[]
        ))

        xgraph.add(XLayer(
            name='in2',
            type=['Input'],
            bottoms=[],
            tops=[],
            targets=[]
        ))

        xgraph.add(XLayer(
            name='conv1',
            type=['Convolution'],
            bottoms=['in1'],
            tops=[],
            data=ConvData(
                weights=np.array([[[[1, 2], [3, 4]]]], dtype=np.float32),
                biases=np.array([0., 1.], dtype=np.float32)
            ),
            targets=[]
        ))

        xgraph.add(XLayer(
            name='add1',
            type=['Eltwise'],
            bottoms=['conv1', 'in2'],
            tops=[],
            targets=[]
        ))

        xgraph.insert(XLayer(
            name='conv2',
            type=['Convolution'],
            bottoms=['in2'],
            tops=['add1'],
            data=ConvData(
                weights=np.array([[[[1, 2], [3, 4]]]], dtype=np.float32),
                biases=np.array([0., 1.], dtype=np.float32)
            ),
            targets=[]
        ))

        xgraph.add(XLayer(
            name='pool1',
            type=['Pooling'],
            bottoms=['add1'],
            tops=[],
            targets=[]
        ))
        xgraph = partition(xgraph, ['cpu'])
        assert len(xgraph) == 6
        xlayers = xgraph.get_layers()
        assert xgraph.get_layer_names() == \
            ['in1', 'conv1', 'in2', 'conv2', 'add1', 'pool1']
        assert set(xlayers[0].targets) == set(['cpu', 'qsim'])
        assert set(xlayers[1].targets) == set(['cpu', 'qsim', 'test'])
        assert set(xlayers[2].targets) == set(['cpu', 'qsim'])
        assert set(xlayers[3].targets) == set(['cpu', 'qsim', 'test'])
        assert set(xlayers[4].targets) == set(['cpu', 'qsim'])
        assert set(xlayers[5].targets) == set(['cpu', 'qsim', 'test'])

        xgraph.remove('conv1')
        assert len(xgraph) == 5
        xlayers = xgraph.get_layers()

        assert xgraph.get_layer_names() == \
            ['in1', 'in2', 'conv2', 'add1', 'pool1']

        assert xlayers[3].type[0] == 'Eltwise'
        assert xlayers[3].bottoms == ['in1', 'conv2']

        assert set(xlayers[0].targets) == set(['cpu', 'qsim'])
        assert set(xlayers[1].targets) == set(['cpu', 'qsim'])
        assert set(xlayers[2].targets) == set(['cpu', 'qsim', 'test'])
        assert set(xlayers[3].targets) == set(['cpu', 'qsim'])
        assert set(xlayers[4].targets) == set(['cpu', 'qsim', 'test'])
                 bn_handling=BatchNormHandling.MERGE_AND_QUANTIZE)

# Finetune the model
# . . .

# Export to ONNX
onnx_filename = 'dpuv2_resnet18.onnx'
export_dpuv2_onnx(model,
                  input_shape=IN_SIZE,
                  input_t=inp,
                  export_path=onnx_filename)

# Load ONNX into PyXIR
onnx_model = onnx.load(onnx_filename)
xgraph = from_onnx(onnx_model)
xgraph = pyxir.partition(xgraph, [target])
xgraph = pyxir.optimize(xgraph, target)
work_dir = os.path.join(file_dir, f'{target}_quant_trained_resnet18_workdir')
inputs = np.random.randn(*IN_SIZE)


def inputs_func(iter):
    return {'inp.1': inputs}


xgraph = pyxir.quantize(xgraph, target, inputs_func, work_dir=work_dir)
pyxir.build(xgraph,
            target,
            work_dir=work_dir,
            build_dir=work_dir,
            runtime='cpu-np')
Exemple #11
0
    def test_inception_like_block(self):
        net = [
            XLayer(name='in1',
                   type=['Input'],
                   shapes=[1, 1, 4, 4],
                   sizes=[16],
                   bottoms=[],
                   tops=['concat1'],
                   layer=['in1'],
                   targets=[]),
            XLayer(name='in2',
                   type=['Input'],
                   shapes=[1, 1, 4, 4],
                   sizes=[16],
                   bottoms=[],
                   tops=['concat1'],
                   layer=['in2'],
                   targets=[]),
            XLayer(name='concat1',
                   type=['Concat'],
                   shapes=[1, 2, 4, 4],
                   sizes=[32],
                   bottoms=['in1', 'in2'],
                   tops=['conv1', 'conv2'],
                   layer=['concat1'],
                   attrs={'axis': 1},
                   targets=[]),
            XLayer(name='conv1',
                   type=['Convolution'],
                   shapes=[1, 4, 3, 3],
                   sizes=[],
                   bottoms=['concat1'],
                   tops=['pool1'],
                   layer=['conv1'],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   },
                   targets=[]),
            XLayer(name='pool1',
                   type=['Pooling'],
                   shapes=[1, 4, 2, 2],
                   sizes=[],
                   bottoms=['conv1'],
                   tops=['concat2'],
                   layer=['pool1'],
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   },
                   targets=[]),
            XLayer(name='conv2',
                   type=['Convolution'],
                   shapes=[1, 4, 2, 2],
                   sizes=[],
                   bottoms=['concat1'],
                   tops=['concat2'],
                   layer=['conv2'],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   },
                   targets=[]),
            XLayer(name='concat2',
                   type=['Concat'],
                   shapes=[1, 8, 2, 2],
                   sizes=[32],
                   bottoms=['pool1', 'conv2'],
                   tops=['dense1'],
                   layer=['concat2'],
                   attrs={'axis': 1},
                   targets=[]),
            XLayer(name='dense1',
                   type=['Dense'],
                   shapes=[1, 20],
                   sizes=[20],
                   bottoms=['concat2'],
                   tops=[],
                   layer=['dense1'],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   targets=[])
        ]
        xgraph = TestSubgraphBuildFunc.xgraph_factory.build_from_xlayer(net)
        p_xgraph = partition(xgraph, ['test'])
        dpu_xgraph = TestSubgraphBuildFunc.target_registry\
            .get_target_build_func('test')(p_xgraph)

        layers = dpu_xgraph.get_layers()
        assert len(dpu_xgraph) == 7

        assert layers[0].type[0] == 'Input'
        assert layers[0].name == 'in1'
        assert layers[0].shapes == [1, 1, 4, 4]
        assert layers[0].bottoms == []
        assert layers[0].tops ==\
            ['0_split_conv1_bottom_NCHW-NHWC_conv2_bottom_NCHW-NHWC']
        assert layers[0].target == 'cpu'
        assert layers[0].subgraph is None

        assert layers[1].type[0] == 'Transpose'
        assert layers[1].name ==\
            '0_split_conv1_bottom_NCHW-NHWC_conv2_bottom_NCHW-NHWC'
        assert layers[1].shapes == [1, 4, 4, 1]
        assert layers[1].bottoms == ['in1']
        assert layers[1].tops == ['xp0']
        assert layers[1].target == 'cpu'
        assert layers[1].subgraph is None

        assert layers[2].type[0] == 'Input'
        assert layers[2].name == 'in2'
        assert layers[2].shapes == [1, 1, 4, 4]
        assert layers[2].bottoms == []
        assert layers[2].tops ==\
            ['1_split_conv1_bottom_NCHW-NHWC_conv2_bottom_NCHW-NHWC']
        assert layers[2].target == 'cpu'
        assert layers[2].subgraph is None

        assert layers[3].type[0] == 'Transpose'
        assert layers[3].name ==\
            '1_split_conv1_bottom_NCHW-NHWC_conv2_bottom_NCHW-NHWC'
        assert layers[3].shapes == [1, 4, 4, 1]
        assert layers[3].bottoms == ['in2']
        assert layers[3].tops == ['xp0']
        assert layers[3].target == 'cpu'
        assert layers[3].subgraph is None

        assert layers[4].type[0] == 'TEST'
        assert layers[4].name == 'xp0'
        assert layers[4].shapes == [[1, 2, 2, 8]]
        assert layers[4].bottoms ==\
            ['0_split_conv1_bottom_NCHW-NHWC_conv2_bottom_NCHW-NHWC',
             '1_split_conv1_bottom_NCHW-NHWC_conv2_bottom_NCHW-NHWC']
        assert layers[4].tops == ['concat2']
        assert layers[4].target == 'cpu'
        assert layers[4].subgraph is None
        assert layers[4].tops == ['concat2']
        assert layers[4].attrs['target'] == 'test'
        assert layers[4].attrs['input_names'] == ['xinput0', 'xinput1']
        assert layers[4].attrs['output_names'] == ['concat2']
        assert layers[4].attrs['input_layers']['xinput0'] == ['concat1']
        assert layers[4].attrs['input_layers']['xinput1'] == ['concat1']
        assert layers[4].attrs['output_layers']['concat2'] == ['concat2']
        assert (layers[4].attrs['__bottom_tensors'] == {
            'xinput0':
            ['0_split_conv1_bottom_NCHW-NHWC_conv2_bottom'
             '_NCHW-NHWC'],
            'xinput1':
            ['1_split_conv1_bottom_NCHW-NHWC_conv2_bottom'
             '_NCHW-NHWC']
        })
        assert (layers[4].attrs['orig_bottom_tensors'] == {
            'xinput0': ['in1'],
            'xinput1': ['in2']
        })
        assert layers[4].attrs['__top_tensors'] ==\
            {'concat2':
                ['merge_pool1_top_NHWC-NCHW_conv2_top_NHWC-NCHW']}
        assert layers[4].attrs['orig_top_tensors'] ==\
            {'concat2': ['dense1']}

        assert layers[5].type[0] == 'TupleGetItem'
        assert layers[5].name == 'concat2'
        assert layers[5].shapes == [1, 8, 2, 2]
        assert layers[5].bottoms == ['xp0']
        assert layers[5].tops == ['dense1']

        # assert layers[6].type[0] == 'Transpose'
        # assert layers[6].name ==\
        #     'merge_pool1_top_NHWC-NCHW_conv2_top_NHWC-NCHW'
        # assert layers[6].shapes == [1, 8, 2, 2]
        # assert layers[6].bottoms == ['concat2']
        # assert layers[6].tops == ['dense1']

        assert layers[6].type[0] == 'Dense'
        assert layers[6].name == 'dense1'
        assert layers[6].shapes == [1, 20]
        assert layers[6].bottoms == ['concat2']
        assert layers[6].tops == []
Exemple #12
0
    def test_basic_diff_layout(self):
        net = [
            XLayer(name='in1',
                   type=['Input'],
                   shapes=[1, 1, 4, 4],
                   sizes=[16],
                   bottoms=[],
                   tops=['conv1'],
                   layer=['in1'],
                   targets=[]),
            XLayer(name='in2',
                   type=['Input'],
                   shapes=[1, 2, 2, 2],
                   sizes=[8],
                   bottoms=[],
                   tops=['add1'],
                   layer=['in2'],
                   targets=[]),
            XLayer(name='conv1',
                   type=['Convolution'],
                   shapes=[1, 2, 3, 3],
                   sizes=[18],
                   bottoms=['in1'],
                   tops=['pool1'],
                   layer=['conv1'],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   },
                   targets=[]),
            XLayer(name='pool1',
                   type=['Pooling'],
                   shapes=[1, 2, 2, 2],
                   sizes=[8],
                   bottoms=['conv1'],
                   tops=['add1'],
                   layer=['pool1'],
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   },
                   targets=[]),
            XLayer(name='add1',
                   type=['Eltwise'],
                   shapes=[1, 2, 2, 2],
                   sizes=[8],
                   bottoms=['pool1', 'in2'],
                   tops=[],
                   layer=['add1'],
                   targets=[])
        ]
        xgraph = TestSubgraphBuildFunc.xgraph_factory.build_from_xlayer(net)
        p_xgraph = partition(xgraph, ['test'])
        dpu_xgraph = TestSubgraphBuildFunc.target_registry\
            .get_target_build_func('test')(p_xgraph)

        layers = dpu_xgraph.get_layers()
        # print(layers)
        assert (len(dpu_xgraph) == 6)

        assert (layers[0].type[0] == 'Input')
        assert (layers[0].name == 'in1')
        assert (layers[0].bottoms == [])
        assert (layers[0].tops == ['conv1_bottom_NCHW-NHWC'])

        assert (layers[1].type[0] == 'Transpose')
        assert (layers[1].name == 'conv1_bottom_NCHW-NHWC')
        assert (layers[1].bottoms == ['in1'])
        assert (layers[1].tops == ['xp0'])

        assert (layers[2].type[0] == 'TEST')
        assert (layers[2].bottoms == ['conv1_bottom_NCHW-NHWC'])
        assert (layers[2].tops == ['pool1'])
        assert (layers[2].attrs['target'] == 'test')
        assert (layers[2].attrs['input_names'] == ['xinput0'])
        assert (layers[2].attrs['output_names'] == ['pool1'])
        assert (layers[2].attrs['input_layers']['xinput0'] == ['conv1'])
        assert (layers[2].attrs['output_layers']['pool1'] == ['pool1'])
        assert (layers[2].attrs['__bottom_tensors'] == {
            'xinput0': ['conv1_bottom_NCHW-NHWC']
        })
        assert (layers[2].attrs['orig_bottom_tensors'] == {'xinput0': ['in1']})
        assert (layers[2].attrs['__top_tensors'] == {
            'pool1': ['pool1_top_NHWC-NCHW']
        })
        assert (layers[2].attrs['orig_top_tensors'] == {'pool1': ['add1']})

        assert (layers[3].type[0] == 'TupleGetItem')
        assert (layers[3].bottoms == ['xp0'])
        assert (layers[3].tops == ['add1'])
        assert layers[3].attrs['transpose'] is True
        assert layers[3].attrs['axes'] == [0, 3, 1, 2]

        # assert(layers[4].type[0] == 'Transpose')
        # assert(layers[4].name == 'pool1_top_NHWC-NCHW')
        # assert(layers[4].bottoms == ['pool1'])
        # assert(layers[4].tops == ['add1'])
        # assert layers[4].attrs['axes'] == [0, 3, 1, 2]

        assert layers[4].type[0] == 'Input'
        assert layers[4].name == 'in2'
        assert layers[4].bottoms == []
        assert layers[4].tops == ['add1']

        assert layers[5].type[0] == 'Eltwise'
        assert layers[5].name == 'add1'
        assert layers[5].bottoms == ['pool1', 'in2']
        assert layers[5].tops == []
Exemple #13
0
    def test_multi_top_tensors(self):
        x1 = px.ops.input("in1", shape=[1, 1, 4, 4])
        w1 = px.ops.constant("weight", np.ones((2, 1, 2, 2), dtype=np.float32))
        conv1 = px.ops.conv2d(
            op_name="conv1",
            input_layer=x1,
            weights_layer=w1,
            kernel_size=[2, 2],
        )  # 1, 2, 3, 3
        pool1 = px.ops.pool2d(
            op_name="pool1",
            input_layer=conv1,
            pool_type="Avg",
            pool_size=[2, 2],
        )  # 1, 2, 2, 2
        t1 = px.ops.transpose("t1", pool1, axes=[0, 2, 3, 1], internal=1)
        t2 = px.ops.transpose("t2", pool1, axes=[0, 2, 3, 1], internal=1)
        s1 = px.ops.sqrt("s1", [t1])
        s2 = px.ops.sqrt("s2", [t2])
        s3 = px.ops.sqrt("s3", [t2])
        net = [x1, conv1, pool1, t1, t2, s1, s2, s3]

        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 8
        assert p_xgraph.get_subgraph_names() == ["xp0"]

        p_xlayers = p_xgraph.get_layers()
        assert p_xlayers[0].type[0] in ["Input"]
        assert p_xlayers[1].type[0] in ["Convolution"]
        assert p_xlayers[2].type[0] in ["Pooling"]
        assert p_xlayers[3].type[0] in ["Transpose"]
        assert p_xlayers[4].type[0] in ["Sqrt"]
        assert p_xlayers[5].type[0] in ["Transpose"]
        assert p_xlayers[6].type[0] in ["Sqrt"]
        assert p_xlayers[7].type[0] in ["Sqrt"]

        assert p_xlayers[0].target == "cpu"
        assert p_xlayers[1].target == "test"
        assert p_xlayers[2].target == "test"
        assert p_xlayers[3].target == "cpu"
        assert p_xlayers[4].target == "cpu"
        assert p_xlayers[5].target == "cpu"
        assert p_xlayers[6].target == "cpu"
        assert p_xlayers[7].target == "cpu"

        assert p_xlayers[0].subgraph is None
        assert p_xlayers[1].subgraph == "xp0"
        assert p_xlayers[2].subgraph == "xp0"
        assert p_xlayers[3].subgraph is None
        assert p_xlayers[4].subgraph is None
        assert p_xlayers[5].subgraph is None
        assert p_xlayers[6].subgraph is None
        assert p_xlayers[7].subgraph is None

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp0 = subgraphs[0]
        assert xp0.name == "xp0"
        xp0_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp0.subgraph_data)

        assert xp0.bottoms == ["in1"]
        assert xp0.tops == ["t1", "t2"]
        assert xp0.shapes == [[-1, 2, 2, 2], [-1, 2, 2, 2]]
        assert xp0.sizes == [8, 8]
        assert len(xp0_xgraph) == 3

        __bottom_tensors = xp0.attrs["__bottom_tensors"]
        orig_bottom_tensors = xp0.attrs["orig_bottom_tensors"]

        assert len(__bottom_tensors) == 1
        assert "xinput0" in __bottom_tensors
        assert __bottom_tensors["xinput0"] == ["in1"]

        assert len(orig_bottom_tensors) == 1
        assert "xinput0" in orig_bottom_tensors
        assert orig_bottom_tensors["xinput0"] == ["in1"]

        __top_tensors = xp0.attrs["__top_tensors"]
        orig_top_tensors = xp0.attrs["orig_top_tensors"]

        assert len(__top_tensors) == 1
        assert "pool1" in __top_tensors
        assert __top_tensors["pool1"] == ["t1", "t2"]

        assert len(orig_top_tensors) == 1
        assert "pool1" in orig_top_tensors
        assert orig_top_tensors["pool1"] == ["s1", "s2", "s3"]
    def test_one_subgraph(self):

        W = np.reshape(
            np.array([[[1, 1], [0, 1]], [[3, 4], [-1, 0]]], dtype=np.float32),
            (2, 1, 2, 2))
        B = np.array([1., -1.], dtype=np.float32)

        net = [
            XLayer(name='in1',
                   type=['Input'],
                   shapes=[-1, 1, 4, 4],
                   sizes=[16],
                   bottoms=[],
                   tops=['conv1'],
                   layer=['in1'],
                   targets=[]),
            XLayer(name='conv1',
                   type=['Convolution'],
                   shapes=[-1, 2, 3, 3],
                   sizes=[18],
                   bottoms=['in1'],
                   tops=['pool1'],
                   layer=['conv2d0'],
                   data=ConvData(W, B),
                   attrs={
                       'data_layout': 'NCHW',
                       'kernel_layout': 'OIHW',
                       'shape': [1, 2, 3, 3],
                       'padding': [[0, 0], [0, 0], [0, 0], [0, 0]],
                       'strides': [1, 1],
                       'dilation': [1, 1],
                       'groups': 1
                   },
                   targets=[]),
            XLayer(
                name='pool1',
                type=['Pooling'],
                shapes=[1, 2, 2, 2],
                sizes=[8],
                bottoms=['conv1'],
                tops=['pool2'],
                layer=['pool1'],
                targets=[],
                attrs={
                    'padding': [[0, 0], [0, 0], [0, 0], [0, 0]],
                    'strides': [1, 1],
                    'kernel_size': [2, 2],
                    'insize': [3, 3],
                    # HW
                    'outsize': [2, 2],
                    'data_layout': 'NCHW',
                    'pool_type': 'Max'
                }),
            XLayer(
                name='pool2',
                type=['Pooling'],
                shapes=[1, 2, 1, 1],
                sizes=[2],
                bottoms=['pool1'],
                tops=[],
                layer=['pool2'],
                targets=[],
                attrs={
                    'padding': [[0, 0], [0, 0], [0, 0], [0, 0]],
                    'strides': [1, 1],
                    'kernel_size': [2, 2],
                    'insize': [2, 2],
                    # HW
                    'outsize': [1, 1],
                    'data_layout': 'NCHW',
                    'pool_type': 'Avg'
                })
        ]
        xgraph = TestBaseSubgraphQuantizer.xgraph_factory\
            .build_from_xlayer(net)
        p_xgraph = partition(xgraph, ['test'])

        assert len(p_xgraph.get_layer_names()) == 4
        assert p_xgraph.get_subgraph_names() == ['xp0']

        p_xlayers = p_xgraph.get_layers()
        assert p_xlayers[0].type[0] in ['Input']
        assert p_xlayers[1].type[0] in ['Convolution']
        assert p_xlayers[2].type[0] in ['Pooling']
        assert p_xlayers[3].type[0] in ['Pooling']

        inputs = np.reshape(
            np.array([[1, 1, 1, 1], [1, 1, 1, 1], [1, 1, 1, 1], [1, 1, 1, 1]],
                     dtype=np.float32), (1, 1, 4, 4))

        def inputs_func(iter):
            return {'in1': inputs}

        quantizer = BaseSubgraphQuantizerTest(xgraph=p_xgraph,
                                              inputs_func=inputs_func)
        quantizer.quantize()

        assert 'xp0' in quantizer.test_inputs
        assert 'xinput0' in quantizer.test_inputs['xp0']

        expected = np.reshape(
            np.array([[[4, 4, 4], [4, 4, 4], [4, 4, 4]],
                      [[5, 5, 5], [5, 5, 5], [5, 5, 5]]]), (1, 2, 3, 3))
        np.testing.assert_array_equal(quantizer.test_inputs['xp0']['xinput0'],
                                      expected)
Exemple #15
0
def _create_multi_output_conv2d_nhwc_oihw(
    in_shape,
    w_shape,
    conv_padding,
    conv_strides,
    conv_dilation,
    kernel_layout="OIHW",
    target="DPUCZDX8G-zcu104",
    out_names=["out1", "out2"],
) -> XGraph:

    kernel_w, kernel_h = w_shape[2], w_shape[3]
    W = np.random.randint(-100, 100, size=w_shape).astype(np.float32)
    # B = np.array([1., -1.], dtype=np.float32)
    out_ch = w_shape[kernel_layout.index("O")]

    x1 = px.ops.input("in1", shape=list(in_shape))
    w1 = px.ops.constant("weight", W)
    conv1 = px.ops.conv2d(
        op_name="conv1",
        input_layer=x1,
        weights_layer=w1,
        kernel_size=[kernel_w, kernel_h],
        strides=list(conv_strides),
        padding_hw=list(conv_padding),
        dilation=list(conv_dilation),
        data_layout="NHWC",
    )
    r1 = px.ops.relu("r1", [conv1])

    W2 = np.random.randint(-10, 10, size=(10, out_ch, 1, 1)).astype(np.float32)
    w2 = px.ops.constant("weight2", W2)
    conv2 = px.ops.conv2d(
        op_name=out_names[0],
        input_layer=r1,
        weights_layer=w2,
        kernel_size=[1, 1],
        strides=[1, 1],
        padding_hw=[0, 0],
        dilation=[1, 1],
        data_layout="NHWC",
    )

    W3 = np.random.randint(-10, 10, size=(10, out_ch, 1, 1)).astype(np.float32)
    w3 = px.ops.constant("weight2", W3)
    conv3 = px.ops.conv2d(
        op_name="conv3",
        input_layer=r1,
        weights_layer=w3,
        kernel_size=[1, 1],
        strides=[1, 1],
        padding_hw=[0, 0],
        dilation=[1, 1],
        data_layout="NHWC",
    )
    r3 = px.ops.relu(out_names[1], [conv3])

    net = [x1, conv1, r1, conv2, conv3, r3]
    xgraph = XGRAPH_FACTORY.build_from_xlayer(net)
    xgraph = px.partition(xgraph, [target])
    return xgraph
Exemple #16
0
    def test_xgraph_device_tagging(self):

        xgraph = XGraph()
        xgraph.add(
            XLayer(name="in1", type=["Input"], bottoms=[], tops=[],
                   targets=[]))

        xgraph.add(
            XLayer(name="in2", type=["Input"], bottoms=[], tops=[],
                   targets=[]))

        xgraph.add(
            XLayer(
                name="conv1",
                type=["Convolution"],
                bottoms=["in1"],
                tops=[],
                data=ConvData(
                    weights=np.array([[[[1, 2], [3, 4]]]], dtype=np.float32),
                    biases=np.array([0.0, 1.0], dtype=np.float32),
                ),
                targets=[],
            ))

        xgraph.add(
            XLayer(
                name="add1",
                type=["Eltwise"],
                bottoms=["conv1", "in2"],
                tops=[],
                targets=[],
            ))

        xgraph.insert(
            XLayer(
                name="conv2",
                type=["Convolution"],
                bottoms=["in2"],
                tops=["add1"],
                data=ConvData(
                    weights=np.array([[[[1, 2], [3, 4]]]], dtype=np.float32),
                    biases=np.array([0.0, 1.0], dtype=np.float32),
                ),
                targets=[],
            ))

        xgraph.add(
            XLayer(name="pool1",
                   type=["Pooling"],
                   bottoms=["add1"],
                   tops=[],
                   targets=[]))
        xgraph = partition(xgraph, ["cpu"])
        assert len(xgraph) == 6
        xlayers = xgraph.get_layers()
        assert xgraph.get_layer_names() == [
            "in1",
            "conv1",
            "in2",
            "conv2",
            "add1",
            "pool1",
        ]
        assert set(xlayers[0].targets) == set(["cpu", "qsim"])
        assert set(xlayers[1].targets) == set(["cpu", "qsim", "test"])
        assert set(xlayers[2].targets) == set(["cpu", "qsim"])
        assert set(xlayers[3].targets) == set(["cpu", "qsim", "test"])
        assert set(xlayers[4].targets) == set(["cpu", "qsim"])
        assert set(xlayers[5].targets) == set(["cpu", "qsim", "test"])

        xgraph.remove("conv1")
        assert len(xgraph) == 5
        xlayers = xgraph.get_layers()

        assert xgraph.get_layer_names() == [
            "in1", "in2", "conv2", "add1", "pool1"
        ]

        assert xlayers[3].type[0] == "Eltwise"
        assert xlayers[3].bottoms == ["in1", "conv2"]

        assert set(xlayers[0].targets) == set(["cpu", "qsim"])
        assert set(xlayers[1].targets) == set(["cpu", "qsim"])
        assert set(xlayers[2].targets) == set(["cpu", "qsim", "test"])
        assert set(xlayers[3].targets) == set(["cpu", "qsim"])
        assert set(xlayers[4].targets) == set(["cpu", "qsim", "test"])
Exemple #17
0
def _create_resnetv1_block(
    in_shape,
    pool_size,
    pool_strides,
    w1_shape,
    w2_shape,
    w3_shape,
    w4_shape,
    c1_padding=[0, 0, 0, 0],
    c2_padding=[0, 0, 0, 0],
    c3_padding=[0, 0, 0, 0],
    c4_padding=[0, 0, 0, 0],
    c1_strides=[1, 1],
    c2_strides=[1, 1],
    c3_strides=[1, 1],
    c4_strides=[1, 1],
    c1_dilation=[1, 1],
    c2_dilation=[1, 1],
    c3_dilation=[1, 1],
    c4_dilation=[1, 1],
    kernel_layout="OIHW",
    target="DPUCZDX8G-zcu104",
) -> XGraph:

    x1 = px.ops.input("in1", shape=list(in_shape))
    pool1 = px.ops.pool2d(
        op_name="pool1",
        input_layer=x1,
        pool_type="Max",
        pool_size=pool_size,
        padding=[0, 0],
        strides=pool_strides,
        layout="NHWC",
    )

    W1 = np.random.randint(-10, 10, size=w1_shape).astype(np.float32)
    w1 = px.ops.constant("w1", W1)
    conv1 = px.ops.conv2d(
        op_name="conv1",
        input_layer=pool1,
        weights_layer=w1,
        kernel_size=[w1_shape[2], w1_shape[3]],
        strides=list(c1_strides),
        padding_hw=list(c1_padding),
        dilation=list(c1_dilation),
        groups=1,
        data_layout="NHWC",
    )

    W2 = np.random.randint(-10, 10, size=w2_shape).astype(np.float32)
    w2 = px.ops.constant("w2", W2)
    conv2 = px.ops.conv2d(
        op_name="conv2",
        input_layer=pool1,
        weights_layer=w2,
        kernel_size=[w2_shape[2], w2_shape[3]],
        strides=list(c2_strides),
        padding_hw=list(c2_padding),
        dilation=list(c2_dilation),
        groups=1,
        data_layout="NHWC",
    )

    W3 = np.random.randint(-10, 10, size=w3_shape).astype(np.float32)
    w3 = px.ops.constant("w3", W3)
    conv3 = px.ops.conv2d(
        op_name="conv3",
        input_layer=conv2,
        weights_layer=w3,
        kernel_size=[w3_shape[2], w3_shape[3]],
        strides=list(c3_strides),
        padding_hw=list(c3_padding),
        dilation=list(c3_dilation),
        groups=1,
        data_layout="NHWC",
    )

    W4 = np.random.randint(-10, 10, size=w4_shape).astype(np.float32)
    w4 = px.ops.constant("w4", W4)
    conv4 = px.ops.conv2d(
        op_name="conv4",
        input_layer=conv3,
        weights_layer=w4,
        kernel_size=[w4_shape[2], w4_shape[3]],
        strides=list(c4_strides),
        padding_hw=list(c4_padding),
        dilation=list(c4_dilation),
        groups=1,
        data_layout="NHWC",
    )

    add = px.ops.eltwise("add", conv1, conv4)

    net = [x1, pool1, conv1, conv2, conv3, conv4, add]
    xgraph = XGRAPH_FACTORY.build_from_xlayer(net)
    xgraph = px.partition(xgraph, [target])
    return xgraph
Exemple #18
0
def _create_scale_conv2d_nhwc_oihw(
    in_shape,
    w_shape,
    conv_padding,
    conv_strides,
    conv_dilation,
    conv_groups=1,
    kernel_layout="OIHW",
    target="DPUCZDX8G-zcu104",
) -> XGraph:

    kernel_w, kernel_h = w_shape[2], w_shape[3]
    in_ch = w_shape[0]

    Gamma = np.random.randint(0, 2, size=(in_ch,))
    Beta = np.random.randint(0, 2, size=(in_ch,))
    W = np.random.randint(-10, 10, size=w_shape).astype(np.float32)
    # B = np.array([1., -1.], dtype=np.float32)

    x1 = px.ops.input("in1", shape=list(in_shape))
    w1 = px.ops.constant("weight", W)
    conv1 = px.ops.conv2d(
        op_name="conv1",
        input_layer=x1,
        weights_layer=w1,
        kernel_size=[kernel_w, kernel_h],
        strides=list(conv_strides),
        padding_hw=list(conv_padding),
        dilation=list(conv_dilation),
        groups=conv_groups,
        data_layout="NHWC",
    )

    pool1 = px.ops.pool2d(
        op_name="pool1",
        input_layer=conv1,
        pool_type="Max",
        pool_size=[3, 3],
        padding=[0, 0],
        layout="NHWC",
    )

    g1 = px.ops.constant("gamma", Gamma)
    b1 = px.ops.constant("beta", Beta)
    scale = px.ops.scale("scale1", pool1, g1, b1, axis=3)
    r1 = px.ops.relu("r1", [scale])

    W2 = np.random.randint(-10, 10, size=(in_ch, in_ch, 1, 1)).astype(np.float32)
    w2 = px.ops.constant("weight2", W2)
    conv2 = px.ops.conv2d(
        op_name="conv2",
        input_layer=r1,
        weights_layer=w2,
        kernel_size=[1, 1],
        strides=[1, 1],
        padding_hw=[0, 0],
        dilation=[1, 1],
        groups=1,
        data_layout="NHWC",
    )

    net = [x1, conv1, pool1, scale, r1, conv2]
    xgraph = XGRAPH_FACTORY.build_from_xlayer(net)
    xgraph = px.partition(xgraph, [target])
    return xgraph
Exemple #19
0
    def test_two_partitions_interrupt(self):
        net = [
            XLayer(name='in1',
                   type=['Input'],
                   shapes=[1, 1, 4, 4],
                   sizes=[16],
                   bottoms=[],
                   tops=['conv1'],
                   layer=['in1'],
                   targets=[]),
            XLayer(name='conv1',
                   type=['Convolution'],
                   shapes=[1, 2, 3, 3],
                   sizes=[18],
                   bottoms=['in1'],
                   tops=['pool1', 'bn1'],
                   layer=['conv1'],
                   targets=[],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   }),
            XLayer(name='pool1',
                   type=['Pooling'],
                   shapes=[1, 4, 3, 3],
                   sizes=[36],
                   bottoms=['conv1'],
                   tops=['concat1'],
                   layer=['pool1'],
                   targets=[],
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   }),
            XLayer(name='bn1',
                   type=['BatchNorm'],
                   shapes=[1, 2, 3, 3],
                   sizes=[18],
                   bottoms=['conv1'],
                   tops=['concat1'],
                   layer=['bn1'],
                   data=BatchData(np.array([1, 1]), np.array([0, 0]),
                                  np.array([1, 1]), np.array([0, 0])),
                   targets=[]),
            XLayer(name='concat1',
                   type=['Concat'],
                   shapes=[1, 6, 3, 3],
                   sizes=[54],
                   bottoms=['pool1', 'bn1'],
                   tops=['conv2'],
                   layer=['concat1'],
                   targets=[]),
            XLayer(name='conv2',
                   type=['Convolution'],
                   shapes=[1, 10, 2, 2],
                   sizes=[40],
                   bottoms=['concat1'],
                   tops=[],
                   layer=['conv2'],
                   targets=[],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   })
        ]
        xgraph = TestSubgraphBuildFunc.xgraph_factory\
            .build_from_xlayer(net)

        p_xgraph = partition(xgraph, ['test_simple'])

        dpu_xgraph = TestSubgraphBuildFunc.target_registry\
            .get_target_build_func('test_simple')(p_xgraph)

        layers = dpu_xgraph.get_layers()
        assert len(dpu_xgraph) == 7

        assert layers[0].type[0] == 'Input'
        assert layers[0].bottoms == []
        assert layers[0].tops == ['xp0']

        assert layers[1].type[0] == 'TEST_SIMPLE'
        assert layers[1].shapes == [[1, 2, 3, 3], [1, 4, 3, 3]]
        assert layers[1].bottoms == ['in1']
        assert layers[1].tops == ['conv1', 'pool1']
        assert layers[1].attrs['input_names'] == ['xinput0']
        assert set(layers[1].attrs['output_names']) == set(['pool1', 'conv1'])
        assert layers[1].attrs['target'] == 'test_simple'
        assert layers[1].attrs['__bottom_tensors'] == {'xinput0': ['in1']}
        assert layers[1].attrs['orig_bottom_tensors'] == {'xinput0': ['in1']}
        assert layers[1].attrs['__top_tensors'] == \
            {'conv1': ['bn1'], 'pool1': ['concat1']}
        assert layers[1].attrs['orig_top_tensors'] == \
            {'conv1': ['bn1'], 'pool1': ['concat1']}

        assert layers[2].type[0] == 'TupleGetItem'
        assert layers[2].name == 'pool1'
        assert layers[2].bottoms == ['xp0']
        assert layers[2].shapes == [1, 4, 3, 3]
        assert layers[2].tops == ['concat1']
        assert layers[2].attrs['index'] == 1

        assert layers[3].type[0] == 'TupleGetItem'
        assert layers[3].name == 'conv1'
        assert layers[3].bottoms == ['xp0']
        assert layers[3].shapes == [1, 2, 3, 3]
        assert layers[3].tops == ['bn1']
        assert layers[3].attrs['index'] == 0

        assert layers[4].type[0] == 'BatchNorm'
        assert layers[4].name == 'bn1'
        assert layers[4].bottoms == ['conv1']
        assert layers[4].shapes == [1, 2, 3, 3]
        assert layers[4].tops == ['concat1']

        assert layers[5].type[0] == 'Concat'
        assert layers[5].name == 'concat1'
        assert layers[5].bottoms == ['pool1', 'bn1']
        assert layers[5].shapes == [1, 6, 3, 3]
        assert layers[5].tops == ['conv2']

        assert layers[6].type[0] == 'Convolution'
        assert layers[6].name == 'conv2'
        assert layers[6].bottoms == ['concat1']
        assert layers[6].shapes == [1, 10, 2, 2]
        assert layers[6].tops == []
Exemple #20
0
    def test_interrupt_partition_in_add_branch(self):
        x = px.ops.input("in1", shape=[1, 28, 28, 2028])
        w1 = px.ops.constant("weight",
                             np.ones((2048, 2048, 1, 1), dtype=np.float32))
        conv1 = px.ops.conv2d(
            op_name="conv1",
            input_layer=x,
            weights_layer=w1,
            kernel_size=[1, 1],
            strides=[1, 1],
            padding_hw=[0, 0, 0, 0],
            dilation=[1, 1],
            groups=1,
            channels=2048,
            data_layout="NHWC",
            kernel_layout="OIHW",
        )
        r1 = px.ops.relu("r1", [conv1])
        w2 = px.ops.constant("weight",
                             np.ones((512, 2048, 1, 1), dtype=np.float32))
        conv2 = px.ops.conv2d(
            op_name="conv2",
            input_layer=r1,
            weights_layer=w2,
            kernel_size=[1, 1],
            strides=[1, 1],
            padding_hw=[0, 0, 0, 0],
            dilation=[1, 1],
            groups=1,
            channels=512,
            data_layout="NHWC",
            kernel_layout="OIHW",
        )
        sigm = px.ops.sigmoid("sigm", [conv2])  # Unsupported layer
        w3 = px.ops.constant("weight",
                             np.ones((2048, 512, 1, 1), dtype=np.float32))
        conv3 = px.ops.conv2d(
            op_name="conv3",
            input_layer=sigm,
            weights_layer=w3,
            kernel_size=[1, 1],
            strides=[1, 1],
            padding_hw=[0, 0, 0, 0],
            dilation=[1, 1],
            groups=1,
            channels=2048,
            data_layout="NHWC",
            kernel_layout="OIHW",
        )  # Although this layer is supported, it should not be in the partition
        add = px.ops.eltwise(
            "add", r1, conv3
        )  # Although this layer is supported, it should not be in the partition
        net = [x, conv1, r1, conv2, sigm, conv3, add]
        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 7
        assert p_xgraph.get_subgraph_names() == ["xp0"]

        p_xlayers = p_xgraph.get_layers()

        assert p_xgraph.get("in1").target == "cpu"
        assert p_xgraph.get("conv1").target == "test"
        assert p_xgraph.get("r1").target == "test"
        assert p_xgraph.get("conv2").target == "test"
        assert p_xgraph.get("sigm").target == "cpu"
        assert p_xgraph.get("conv3").target == "cpu"
        assert p_xgraph.get("add").target == "cpu"

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp0 = subgraphs[0]
        assert xp0.name == "xp0"
        xp0_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp0.subgraph_data)

        assert xp0.bottoms == ["in1"]
        assert xp0.tops == ["add", "sigm"]
        assert xp0.shapes == [[-1, 28, 28, 2048], [-1, 28, 28, 512]]
        assert xp0.sizes == [28 * 28 * 2048, 28 * 28 * 512]

        assert len(xp0_xgraph) == 4
        xp0_layers = xp0_xgraph.get_layers()

        assert xp0_layers[0].type[0] == "Input"
        assert xp0_layers[0].layer[0] == "conv1"
        assert xp0_layers[1].type[0] == "Convolution"
        assert xp0_layers[2].type[0] == "ReLU"
        assert xp0_layers[3].type[0] == "Convolution"
Exemple #21
0
    def test_two_partition_diff_layout(self):
        net = [
            XLayer(name='in1',
                   type=['Input'],
                   shapes=[1, 1, 4, 4],
                   sizes=[16],
                   bottoms=[],
                   tops=['conv1'],
                   layer=['in1'],
                   targets=[]),
            XLayer(name='in2',
                   type=['Input'],
                   shapes=[1, 4, 4, 1],
                   sizes=[16],
                   bottoms=[],
                   tops=['in2_transpose'],
                   layer=['in2'],
                   targets=[]),
            XLayer(name='in2_transpose',
                   type=['Transpose'],
                   shapes=[1, 1, 4, 4],
                   sizes=[16],
                   bottoms=['in2'],
                   tops=['conv2'],
                   layer=['in2'],
                   attrs={'axes': [0, 3, 1, 2]},
                   targets=[]),
            XLayer(name='conv1',
                   type=['Convolution'],
                   shapes=[1, 2, 3, 3],
                   sizes=[18],
                   bottoms=['in1'],
                   tops=['pool1'],
                   layer=['conv1'],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   },
                   targets=[]),
            XLayer(name='pool1',
                   type=['Pooling'],
                   shapes=[1, 2, 2, 2],
                   sizes=[8],
                   bottoms=['conv1'],
                   tops=['concat1'],
                   layer=['pool1'],
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   },
                   targets=[]),
            XLayer(name='conv2',
                   type=['Convolution'],
                   shapes=[1, 2, 2, 2],
                   sizes=[8],
                   bottoms=['in2_transpose'],
                   tops=['concat1'],
                   layer=['conv2'],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   attrs={
                       'data_layout': 'NCHW',
                       'padding': [[0, 0], [0, 0], [1, 1], [1, 1]]
                   },
                   targets=[]),
            XLayer(name='concat1',
                   type=['Concat'],
                   shapes=[1, 4, 2, 2],
                   sizes=[16],
                   bottoms=['pool1', 'conv2'],
                   tops=['concat1_transpose'],
                   layer=['concat1'],
                   attrs={'axis': 1},
                   targets=[]),
            XLayer(name='concat1_transpose',
                   type=['Transpose'],
                   shapes=[1, 2, 2, 4],
                   sizes=[16],
                   bottoms=['concat1'],
                   tops=['dense1'],
                   layer=['concat1'],
                   attrs={'axes': [0, 2, 3, 1]},
                   targets=[]),
            XLayer(name='dense1',
                   type=['Dense'],
                   shapes=[1, 20],
                   sizes=[],
                   bottoms=['concat1_transpose'],
                   tops=[],
                   data=ConvData(np.array([1, 1]), np.array([0, 0])),
                   layer=['dense1'],
                   targets=[])
        ]
        xgraph = TestSubgraphBuildFunc.xgraph_factory.build_from_xlayer(net)
        p_xgraph = partition(xgraph, ['test'])
        p_xlayers = p_xgraph.get_layers()

        dpu_xgraph = TestSubgraphBuildFunc.target_registry\
            .get_target_build_func('test')(p_xgraph)

        layers = dpu_xgraph.get_layers()
        assert len(dpu_xgraph) == 6

        assert layers[0].type[0] == 'Input'
        assert layers[0].name == 'in1'
        assert layers[0].shapes == [1, 1, 4, 4]
        assert layers[0].bottoms == []
        assert layers[0].tops == ['conv1_bottom_NCHW-NHWC']
        assert layers[0].target == 'cpu'
        assert layers[0].subgraph is None

        assert layers[1].type[0] == 'Transpose'
        assert layers[1].name == 'conv1_bottom_NCHW-NHWC'
        assert layers[1].shapes == [1, 4, 4, 1]
        assert layers[1].bottoms == ['in1']
        assert layers[1].tops == ['xp2']
        assert layers[1].target == 'cpu'
        assert layers[1].subgraph is None

        assert layers[2].type[0] == 'Input'
        assert layers[2].name == 'in2'
        assert layers[2].shapes == [1, 4, 4, 1]
        assert layers[2].bottoms == []
        assert layers[2].tops == ['xp2']
        assert layers[2].target == 'cpu'
        assert layers[2].subgraph is None

        assert layers[3].type[0] == 'TEST'
        assert layers[3].name == 'xp2'
        assert layers[3].shapes == [[1, 2, 2, 4]]
        assert layers[3].bottoms == ['conv1_bottom_NCHW-NHWC', 'in2']
        assert layers[3].tops == ['concat1']
        assert layers[3].target == 'cpu'
        assert layers[3].subgraph is None
        assert layers[3].attrs['target'] == 'test'
        assert layers[3].attrs['input_names'] == ['xinput0', 'xinput1']
        assert layers[3].attrs['output_names'] == ['concat1']
        assert layers[3].attrs['input_layers']['xinput0'] == ['conv1']
        assert layers[3].attrs['input_layers']['xinput1'] == ['conv2']
        assert layers[3].attrs['output_layers']['concat1'] == ['concat1']
        assert (layers[3].attrs['__bottom_tensors'] == {
            'xinput0': ['conv1_bottom_NCHW-NHWC'],
            'xinput1': ['in2']
        })
        assert (layers[3].attrs['orig_bottom_tensors'] == {
            'xinput0': ['in1'],
            'xinput1': ['in2']
        })
        assert layers[3].attrs['__top_tensors'] == {'concat1': ['dense1']}
        assert layers[3].attrs['orig_top_tensors'] == {'concat1': ['dense1']}

        assert layers[4].type[0] == 'TupleGetItem'
        assert layers[4].name == 'concat1'
        assert layers[4].shapes == [1, 2, 2, 4]
        assert layers[4].bottoms == ['xp2']
        assert layers[4].tops == ['dense1']
        assert layers[4].target == 'cpu'
        assert layers[4].subgraph is None

        assert layers[5].type[0] == 'Dense'
        assert layers[5].name == 'dense1'
        assert layers[5].shapes == [1, 20]
        assert layers[5].bottoms == ['concat1']
        assert layers[5].tops == []
        assert layers[5].target == 'cpu'
        assert layers[5].subgraph is None
Exemple #22
0
    def test_complete_partition(self):
        x = px.ops.input("in1", shape=[1, 1, 4, 4])
        w1 = px.ops.constant("weight", np.ones((2, 1, 2, 2), dtype=np.float32))
        conv = px.ops.conv2d(
            op_name="conv1",
            input_layer=x,
            weights_layer=w1,
            kernel_size=[2, 2],
        )
        pool = px.ops.pool2d(
            op_name="pool1",
            input_layer=conv,
            pool_type="Avg",
            pool_size=[2, 2],
        )
        net = [x, conv, pool]
        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 3
        assert p_xgraph.get_subgraph_names() == ["xp0"]

        p_xlayers = p_xgraph.get_layers()
        assert p_xlayers[0].type[0] in ["Input"]
        assert p_xlayers[1].type[0] in ["Convolution"]
        assert p_xlayers[2].type[0] in ["Pooling"]

        assert p_xlayers[0].target == "cpu"
        assert p_xlayers[1].target == "test"
        assert p_xlayers[2].target == "test"

        assert p_xlayers[0].subgraph is None
        assert p_xlayers[1].subgraph == "xp0"
        assert p_xlayers[2].subgraph == "xp0"

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp0 = subgraphs[0]
        assert xp0.name == "xp0"
        xp0_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp0.subgraph_data)

        assert xp0.bottoms == ["in1"]
        assert xp0.tops == []
        assert xp0.shapes == [[-1, 2, 2, 2]]
        assert xp0.sizes == [8]
        assert xp0.attrs["target"] == "test"
        assert xp0.attrs["__bottom_tensors"] == {"xinput0": ["in1"]}
        assert xp0.attrs["orig_bottom_tensors"] == {"xinput0": ["in1"]}
        assert xp0.attrs["__top_tensors"] == {"pool1": []}
        assert xp0.attrs["orig_top_tensors"] == {"pool1": []}

        assert len(xp0_xgraph) == 3
        xp0_layers = xp0_xgraph.get_layers()

        assert xp0_layers[0].type[0] == "Input"
        assert xp0_layers[0].layer[0] == "conv1"
        assert xp0_layers[1].type[0] == "Convolution"
        assert xp0_layers[2].type[0] == "Pooling"

        assert xp0_layers[0].bottoms == []
        assert xp0_layers[0].tops == ["conv1"]
        assert xp0_layers[1].bottoms == ["xinput0"]
        assert xp0_layers[1].tops == ["pool1"]
        assert xp0_layers[2].bottoms == ["conv1"]
        assert xp0_layers[2].tops == []
Exemple #23
0
    def test_two_partitions_through_interruption(self):
        # A layer inside a residual type branch os not supported
        # Here: BatchNorm
        x1 = px.ops.input("in1", shape=[1, 1, 4, 4])
        w1 = px.ops.constant("weight", np.ones((2, 1, 2, 2), dtype=np.float32))
        conv1 = px.ops.conv2d(
            op_name="conv1",
            input_layer=x1,
            weights_layer=w1,
            kernel_size=[2, 2],
        )  # 1, 2, 3, 3
        pool = px.ops.pool2d(
            op_name="pool1",
            input_layer=conv1,
            pool_type="Avg",
            pool_size=[2, 2],
            padding=[1, 1, 0, 0],
        )  # 1, 2, 3, 3
        bn_mean = px.ops.constant("mean", np.ones((2, ), dtype=np.float32))
        bn_var = px.ops.constant("var", np.ones((2, ), dtype=np.float32))
        bn_gamma = px.ops.constant("gamma", np.ones((2, ), dtype=np.float32))
        bn_beta = px.ops.constant("beta", np.ones((2, ), dtype=np.float32))
        bn = px.ops.batch_norm(
            op_name="bn1",
            input_layer=conv1,
            mean_layer=bn_mean,
            variance_layer=bn_var,
            gamma_layer=bn_gamma,
            beta_layer=bn_beta,
            axis=1,
        )  # 1, 2, 3, 3
        concat = px.ops.concat("concat1", [pool, bn], axis=1)  # 1, 4, 3, 3
        w2 = px.ops.constant("weight2", np.ones((6, 2, 2, 2),
                                                dtype=np.float32))
        conv2 = px.ops.conv2d(
            op_name="conv2",
            input_layer=concat,
            weights_layer=w2,
            kernel_size=[2, 2],
            padding_hw=[1, 1, 0, 0],
        )  # 1, 6, 3, 3
        net = [x1, conv1, pool, bn, concat, conv2]
        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 6
        assert p_xgraph.get_subgraph_names() == ["xp0"]

        p_xlayers = p_xgraph.get_layers()
        assert p_xlayers[0].type[0] in ["Input"]
        assert p_xlayers[1].type[0] in ["Convolution"]
        assert p_xlayers[2].type[0] in ["Pooling"]
        assert p_xlayers[3].type[0] in ["BatchNorm"]
        assert p_xlayers[4].type[0] in ["Concat"]
        assert p_xlayers[5].type[0] in ["Convolution"]

        assert p_xlayers[0].target == "cpu"
        assert p_xlayers[1].target == "test"
        assert p_xlayers[2].target == "test"
        assert p_xlayers[3].target == "cpu"
        assert p_xlayers[4].target == "cpu"
        assert p_xlayers[5].target == "cpu"

        assert p_xlayers[0].subgraph is None
        assert p_xlayers[1].subgraph == "xp0"
        assert p_xlayers[2].subgraph == "xp0"
        assert p_xlayers[3].subgraph is None
        assert p_xlayers[4].subgraph is None
        assert p_xlayers[5].subgraph is None

        assert p_xlayers[3].name == "bn1"
        assert p_xlayers[3].bottoms == ["conv1"]
        assert p_xlayers[3].tops == ["concat1"]

        assert p_xlayers[4].name == "concat1"
        assert p_xlayers[4].bottoms == ["pool1", "bn1"]
        assert p_xlayers[4].tops == ["conv2"]

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp0 = subgraphs[0]
        assert xp0.name == "xp0"
        xp0_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp0.subgraph_data)

        assert xp0.bottoms == ["in1"]
        assert xp0.tops == ["bn1", "concat1"]
        assert xp0.shapes == [[-1, 2, 3, 3], [-1, 2, 3, 3]]
        assert xp0.sizes == [18, 18]
        assert xp0.attrs["target"] == "test"
        assert xp0.attrs["__bottom_tensors"] == {"xinput0": ["in1"]}
        assert xp0.attrs["orig_bottom_tensors"] == {"xinput0": ["in1"]}
        assert xp0.attrs["__top_tensors"] == {
            "conv1": ["bn1"],
            "pool1": ["concat1"]
        }
        assert xp0.attrs["orig_top_tensors"] == {
            "conv1": ["bn1"],
            "pool1": ["concat1"]
        }

        assert len(xp0_xgraph) == 3
        xp0_layers = xp0_xgraph.get_layers()

        assert [X.name for X in xp0_xgraph.get_input_layers()] == ["xinput0"]
        # TODO: XGraph only recognizes output layers when they have no top
        #   layers
        assert [X.name for X in xp0_xgraph.get_output_layers()] == ["pool1"]

        assert xp0_layers[0].type[0] == "Input"
        assert xp0_layers[0].layer[0] == "conv1"
        assert xp0_layers[1].type[0] == "Convolution"
        assert xp0_layers[2].type[0] == "Pooling"

        assert xp0_layers[0].bottoms == []
        assert xp0_layers[0].tops == ["conv1"]
        assert xp0_layers[1].bottoms == ["xinput0"]
        assert xp0_layers[1].tops == ["pool1"]
        assert xp0_layers[2].bottoms == ["conv1"]
        assert xp0_layers[2].tops == []
Exemple #24
0
    def test_multiple_partitions(self):
        x1 = px.ops.input("in1", shape=[1, 1, 4, 4])
        x2 = px.ops.input("in2", shape=[1, 2, 2, 2])
        w1 = px.ops.constant("weight", np.ones((2, 1, 2, 2), dtype=np.float32))
        conv1 = px.ops.conv2d(
            op_name="conv1",
            input_layer=x1,
            weights_layer=w1,
            kernel_size=[2, 2],
        )  # 1, 2, 3, 3
        pool = px.ops.pool2d(
            op_name="pool1",
            input_layer=conv1,
            pool_type="Avg",
            pool_size=[2, 2],
        )  # 1, 2, 2, 2
        add = px.ops.eltwise("add1", pool, x2)  # 1, 2, 2, 2
        bn_mean = px.ops.constant("mean", np.ones((2, ), dtype=np.float32))
        bn_var = px.ops.constant("var", np.ones((2, ), dtype=np.float32))
        bn_gamma = px.ops.constant("gamma", np.ones((2, ), dtype=np.float32))
        bn_beta = px.ops.constant("beta", np.ones((2, ), dtype=np.float32))
        bn = px.ops.batch_norm(
            op_name="bn1",
            input_layer=add,
            mean_layer=bn_mean,
            variance_layer=bn_var,
            gamma_layer=bn_gamma,
            beta_layer=bn_beta,
            axis=1,
        )  # 1, 2, 3, 3
        pool2 = px.ops.pool2d(
            op_name="pool2",
            input_layer=bn,
            pool_type="Avg",
            pool_size=[2, 2],
            padding=[0, 0, 1, 1],
        )  # 1, 2, 2, 2
        net = [x1, x2, conv1, pool, add, bn, pool2]
        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 7
        # ! Only xp0 because only one subgraph can exist for now (largest)
        assert set(p_xgraph.get_subgraph_names()) == set(["xp0"])

        p_xlayers = p_xgraph.get_layers()
        assert p_xlayers[0].type[0] in ["Input"]
        assert p_xlayers[1].type[0] in ["Convolution"]
        assert p_xlayers[2].type[0] in ["Pooling"]
        assert p_xlayers[3].type[0] in ["Input"]
        assert p_xlayers[4].type[0] in ["Eltwise"]
        assert p_xlayers[5].type[0] in ["BatchNorm"]
        assert p_xlayers[6].type[0] in ["Pooling"]

        assert p_xlayers[0].target == "cpu"
        assert p_xlayers[1].target == "test"
        assert p_xlayers[2].target == "test"
        assert p_xlayers[3].target == "cpu"
        assert p_xlayers[4].target == "test"
        assert p_xlayers[5].target == "cpu"
        # ! CPU because only one subgraph can exist for now (largest)
        assert p_xlayers[6].target == "cpu"

        assert p_xlayers[0].subgraph is None
        assert p_xlayers[1].subgraph == "xp0"
        assert p_xlayers[2].subgraph == "xp0"
        assert p_xlayers[3].subgraph is None
        assert p_xlayers[4].subgraph == "xp0"
        assert p_xlayers[5].subgraph is None
        assert p_xlayers[6].subgraph is None

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp0 = subgraphs[0]
        assert xp0.name == "xp0"
        xp0_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp0.subgraph_data)

        assert xp0.bottoms == ["in1", "in2"]
        assert xp0.tops == ["bn1"]
        assert xp0.shapes == [[-1, 2, 2, 2]]
        assert xp0.sizes == [8]

        assert len(xp0_xgraph) == 5
        xp0_layers = xp0_xgraph.get_layers()

        assert xp0_layers[0].type[0] == "Input"
        assert xp0_layers[0].layer[0] == "conv1"
        assert xp0_layers[1].type[0] == "Convolution"
        assert xp0_layers[2].type[0] == "Pooling"
        assert xp0_layers[3].type[0] == "Input"
        assert xp0_layers[4].type[0] == "Eltwise"

        assert xp0_layers[0].bottoms == []
        assert xp0_layers[0].tops == ["conv1"]
        assert xp0_layers[1].bottoms == ["xinput0"]
        assert xp0_layers[1].tops == ["pool1"]
        assert xp0_layers[2].bottoms == ["conv1"]
        assert xp0_layers[2].tops == ["add1"]
Exemple #25
0
    def test_conv_maxpool_subgraph(self):
        W = np.reshape(
            np.array([[[1, 2], [3, 0]], [[1, 1], [0, 1]]], dtype=np.float32),
            (2, 1, 2, 2))
        B = np.array([0., 0.], dtype=np.float32)

        net = [
            XLayer(
                name='in',
                type=['Input'],
                shapes=[1, 1, 4, 4],
                sizes=[16],
                bottoms=[],
                tops=['conv2d0'],
                layer=['in'],
                targets=[]
            ),
            XLayer(
                name='conv2d0',
                type=['Convolution'],
                shapes=[1, 2, 3, 3],
                sizes=[18],
                bottoms=['in'],
                tops=[],
                layer=['conv2d0'],
                data=ConvData(W, B),
                attrs={
                    'data_layout': 'NCHW',
                    'kernel_layout': 'OIHW',
                    'shape': [1, 2, 3, 3],
                    'padding': [[0, 0], [0, 0], [0, 0], [0, 0]],
                    'strides': [1, 1],
                    'dilation': [1, 1],
                    'groups': 1
                },
                targets=[]
            ),
            XLayer(
                name='max_pool2d0',
                type=['Pooling'],
                shapes=[1, 2, 2, 2],
                sizes=[8],
                bottoms=['conv2d0'],
                tops=[],
                layer=['max_pool2d0'],
                attrs={
                    'kernel_size': [2, 2],
                    'insize': [3, 3],
                    'outsize': [2, 2],
                    'data_layout': 'NCHW',
                    'padding': [[0, 0], [0, 0], [0, 0], [0, 0]],
                    'strides': [1, 1],
                    'pool_type': 'Max'
                },
                targets=[]
            )
        ]
        xgraph = TestQuantSimPass.xgraph_factory.build_from_xlayer(
            net, name='testtest'
        )
        p_xgraph = partition(xgraph, ['npu_test'])

        assert p_xgraph.get_layers()[0].target == 'cpu'
        assert p_xgraph.get_layers()[1].target == 'npu_test'
        assert p_xgraph.get_layers()[2].target == 'cpu'

        assert p_xgraph.get_layers()[0].subgraph is None
        assert p_xgraph.get_layers()[1].subgraph == 'xp0'
        assert p_xgraph.get_layers()[2].subgraph is None

        quant_sim_pass = XGraphQuantSimPass(
            fdir=FILE_PATH,
            name=xgraph.get_name() + '_qsim'
        )
        qsim_xgraph = quant_sim_pass.execute(xgraph=p_xgraph,
                                             subgraphs_only=True)

        exec_graph = TestQuantSimPass.xf_exec_graph_factory.build_runtime(
            qsim_xgraph
        )

        inpts = {
            'in': np.reshape(
                np.array([
                    [10, 10, 0, 40],
                    [50, 10, 0, 80],
                    [30, 50, 10, 0],
                    [10, 90, 30, 40]],
                    dtype=np.float32
                ),
                (1, 1, 4, 4))
        }
        res = exec_graph.run(inpts)
        outpt = res[0]

        expected_outpt = np.array([[
            [[182.28346, 189.5748],
             [342.6929, 342.6929]],
            [[109.37008, 123.95275],
             [167.70079, 87.49606]]]],
            dtype=np.float32)

        np.testing.assert_array_almost_equal(outpt, expected_outpt, decimal=4)
Exemple #26
0
    def test_multiple_partitions_largest_last(self):
        x1 = px.ops.input("in1", shape=[1, 1, 4, 4])
        w1 = px.ops.constant("weight1", np.ones((2, 1, 2, 2),
                                                dtype=np.float32))
        conv1 = px.ops.conv2d(
            op_name="conv1",
            input_layer=x1,
            weights_layer=w1,
            kernel_size=[2, 2],
        )  # 1, 2, 3, 3
        t1 = px.ops.transpose("t1", conv1, axes=[0, 2, 3, 1])  # 1, 3, 3, 2
        w2 = px.ops.constant("weight2", np.ones((4, 2, 2, 2),
                                                dtype=np.float32))
        conv2 = px.ops.conv2d(
            op_name="conv2",
            input_layer=t1,
            weights_layer=w2,
            kernel_size=[2, 2],
            padding_hw=[1, 0, 1, 0],
            data_layout="NHWC",
        )  # 1, 3, 3, 4
        pool = px.ops.pool2d(
            op_name="pool1",
            input_layer=conv2,
            pool_type="Avg",
            pool_size=[2, 2],
            layout="NHWC",
        )  # 1, 2, 2, 4
        net = [x1, conv1, t1, conv2, pool]
        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 5
        # ! Only xp1 because only one subgraph can exist for now (largest)
        assert set(p_xgraph.get_subgraph_names()) == set(["xp1"])

        p_xlayers = p_xgraph.get_layers()
        assert p_xlayers[0].type[0] in ["Input"]
        assert p_xlayers[1].type[0] in ["Convolution"]
        assert p_xlayers[2].type[0] in ["Transpose"]
        assert p_xlayers[3].type[0] in ["Convolution"]
        assert p_xlayers[4].type[0] in ["Pooling"]

        assert p_xlayers[0].target == "cpu"
        assert p_xlayers[1].target == "cpu"
        assert p_xlayers[2].target == "cpu"
        assert p_xlayers[3].target == "test"
        assert p_xlayers[4].target == "test"

        assert p_xlayers[0].subgraph is None
        assert p_xlayers[1].subgraph is None
        assert p_xlayers[2].subgraph is None
        assert p_xlayers[3].subgraph == "xp1"
        assert p_xlayers[4].subgraph == "xp1"

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp1 = subgraphs[0]
        assert xp1.name == "xp1"
        xp1_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp1.subgraph_data)

        assert xp1.bottoms == ["t1"]
        assert xp1.tops == []
        assert xp1.shapes == [[-1, 2, 2, 4]]
        assert xp1.sizes == [16]

        assert len(xp1_xgraph) == 3
        xp1_layers = xp1_xgraph.get_layers()

        assert xp1_layers[0].type[0] == "Input"
        assert xp1_layers[0].layer[0] == "conv2"
        assert xp1_layers[1].type[0] == "Convolution"
        assert xp1_layers[2].type[0] == "Pooling"

        assert xp1_layers[0].bottoms == []
        assert xp1_layers[0].tops == ["conv2"]
        assert xp1_layers[1].bottoms == ["xinput0"]
        assert xp1_layers[1].tops == ["pool1"]
        assert xp1_layers[2].bottoms == ["conv2"]
        assert xp1_layers[2].tops == []
Exemple #27
0
    def test_small(self):
        net = [
            XLayer(
                name="in1",
                type=["Input"],
                shapes=[1, 1, 4, 4],
                sizes=[16],
                bottoms=[],
                tops=["conv1"],
                layer=["in1"],
                targets=[],
            ),
            XLayer(
                name="in2",
                type=["Input"],
                shapes=[1, 2, 2, 2],
                sizes=[8],
                bottoms=[],
                tops=["dense1"],
                layer=["in2"],
                targets=[],
            ),
            XLayer(
                name="conv1",
                type=["Convolution"],
                shapes=[1, 2, 3, 3],
                sizes=[18],
                bottoms=["in1"],
                tops=["pool1"],
                layer=["conv1"],
                data=ConvData(np.array([1, 1]), np.array([0, 0])),
                attrs={
                    "data_layout": "NCHW",
                    "padding": [[0, 0], [0, 0], [1, 1], [1, 1]],
                    "kernel_size": [3, 3],
                    "strides": [1, 1],
                    "dilation": [1, 1],
                    "groups": 1,
                    "channels": [2, 2],
                },
                targets=[],
            ),
            XLayer(
                name="pool1",
                type=["Pooling"],
                shapes=[1, 2, 2, 2],
                sizes=[8],
                bottoms=["conv1"],
                tops=["dense1"],
                layer=["pool1"],
                attrs={
                    "data_layout": "NCHW",
                    "padding": [[0, 0], [0, 0], [1, 1], [1, 1]],
                    "kernel_size": [3, 3],
                    "strides": [1, 1],
                },
                targets=[],
            ),
            XLayer(
                name="dense1",
                type=["Dense"],
                shapes=[1, 20],
                sizes=[20],
                bottoms=["pool1", "in2"],
                tops=[],
                data=ConvData(np.array([1, 1]), np.array([0, 0])),
                layer=["dense1"],
                targets=[],
            ),
        ]
        xgraph = TestDPUCZDX8G.xgraph_factory.build_from_xlayer(net)
        p_xgraph = partition(xgraph, ["dpuv2-zcu104"])
        dpu_xgraph = TestDPUCZDX8G.target_registry.get_target_build_func(
            "dpuv2-zcu104")(p_xgraph)

        assert len(dpu_xgraph) == 6
        layers = dpu_xgraph.get_layers()

        assert layers[0].type[0] == "Input"

        assert layers[1].type[0] == "Transpose"
        assert layers[1].bottoms == ["in1"]
        assert layers[1].tops == ["xp0"]

        assert layers[2].type[0] == "DPU"
        assert layers[2].bottoms == ["conv1_bottom_NCHW-NHWC"]
        assert layers[2].tops == ["pool1"]
        assert layers[2].shapes == [[1, 2, 2, 2]]
        assert layers[2].attrs["target"] == "dpuv2-zcu104"
        assert layers[2].attrs["input_names"] == ["xinput0"]
        assert layers[2].attrs["output_names"] == ["pool1"]
        assert layers[2].attrs["input_layers"]["xinput0"] == ["conv1"]
        assert layers[2].attrs["output_layers"]["pool1"] == ["pool1"]
        assert layers[2].attrs["__top_tensors"] == {
            "pool1": ["pool1_top_NHWC-NCHW"]
        }
        assert layers[2].attrs["orig_top_tensors"] == {"pool1": ["dense1"]}
        assert layers[2].attrs["__bottom_tensors"] == {
            "xinput0": ["conv1_bottom_NCHW-NHWC"]
        }
        assert layers[2].attrs["orig_bottom_tensors"] == {"xinput0": ["in1"]}

        # Merged TupleGetItem and Transpose layer
        assert layers[3].type[0] == "TupleGetItem"
        assert layers[3].name == "pool1"
        assert layers[3].shapes == [1, 2, 2, 2]
        assert layers[3].bottoms == ["xp0"]
        assert layers[3].tops == ["dense1"]
        assert layers[3].attrs["transpose"] is True

        assert layers[4].type[0] == "Input"
        assert layers[4].name == "in2"
        assert layers[4].tops == ["dense1"]

        assert layers[5].type[0] == "Dense"
        assert layers[5].name == "dense1"
        assert layers[5].shapes == [1, 20]
        assert layers[5].bottoms == ["pool1", "in2"]
        assert layers[5].tops == []
Exemple #28
0
    def test_two_partition_inputs(self):
        x1 = px.ops.input("in1", shape=[1, 1, 4, 4])
        x2 = px.ops.input("in2", shape=[1, 1, 4, 4])
        w1 = px.ops.constant("weight", np.ones((2, 1, 2, 2), dtype=np.float32))
        conv1 = px.ops.conv2d(
            op_name="conv1",
            input_layer=x1,
            weights_layer=w1,
            kernel_size=[2, 2],
        )  # 1, 2, 3, 3
        pool = px.ops.pool2d(
            op_name="pool1",
            input_layer=conv1,
            pool_type="Avg",
            pool_size=[3, 3],
        )  # 1, 2, 1, 1
        w2 = px.ops.constant("weight2", np.ones((2, 1, 4, 4),
                                                dtype=np.float32))
        conv2 = px.ops.conv2d(
            op_name="conv2",
            input_layer=x2,
            weights_layer=w2,
            kernel_size=[4, 4],
            strides=[1, 1],
        )  # 1, 2, 1, 1
        add = px.ops.eltwise("add1", pool, conv2)
        reshape = px.ops.reshape("reshape1", add, [-1, 2])
        wd = px.ops.constant("weight_dense", np.ones((20, 2),
                                                     dtype=np.float32))
        dense = px.ops.dense(
            op_name="dense1",
            input_layer=reshape,
            weights_layer=wd,
            units=20,
        )
        net = [x1, x2, conv1, pool, conv2, add, reshape, dense]
        xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(net)
        p_xgraph = px.partition(xgraph, ["test"])

        assert len(p_xgraph.get_layer_names()) == 8
        assert p_xgraph.get_subgraph_names() == ["xp2"]

        p_xlayers = p_xgraph.get_layers()

        assert p_xlayers[0].target == "cpu"
        assert p_xlayers[1].target == "test"
        assert p_xlayers[2].target == "test"
        assert p_xlayers[3].target == "cpu"
        assert p_xlayers[4].target == "test"
        assert p_xlayers[5].target == "test"
        assert p_xlayers[6].target == "cpu"
        assert p_xlayers[7].target == "cpu"

        assert p_xlayers[0].subgraph is None
        assert p_xlayers[1].subgraph == "xp2"
        assert p_xlayers[2].subgraph == "xp2"
        assert p_xlayers[3].subgraph is None
        assert p_xlayers[4].subgraph == "xp2"
        assert p_xlayers[5].subgraph == "xp2"
        assert p_xlayers[6].subgraph is None
        assert p_xlayers[7].subgraph is None

        subgraphs = TestXGraphPartitioner.xgraph_partitioner.get_subgraphs(
            p_xgraph)

        assert len(subgraphs) == 1
        xp2 = subgraphs[0]
        assert xp2.name == "xp2"
        xp2_xgraph = TestXGraphPartitioner.xgraph_factory.build_from_xlayer(
            xp2.subgraph_data)

        assert xp2.bottoms == ["in1", "in2"]
        assert xp2.tops == ["reshape1"]
        assert xp2.shapes == [[-1, 2, 1, 1]]
        assert xp2.sizes == [2]

        assert len(xp2_xgraph) == 6
        xp2_layers = xp2_xgraph.get_layers()

        assert xp2_layers[0].type[0] == "Input"
        assert xp2_layers[0].layer[0] == "conv1"
        assert xp2_layers[1].type[0] == "Convolution"
        assert xp2_layers[2].type[0] == "Pooling"
        assert xp2_layers[3].type[0] == "Input"
        assert xp2_layers[3].layer[0] == "conv2"
        assert xp2_layers[4].type[0] == "Convolution"
        assert xp2_layers[5].type[0] == "Eltwise"

        assert xp2_layers[0].bottoms == []
        assert xp2_layers[0].tops == ["conv1"]
        assert xp2_layers[1].bottoms == ["xinput0"]
        assert xp2_layers[1].tops == ["pool1"]
        assert xp2_layers[2].bottoms == ["conv1"]
        assert xp2_layers[2].tops == ["add1"]
        assert xp2_layers[3].bottoms == []
        assert xp2_layers[3].tops == ["conv2"]
        assert xp2_layers[4].bottoms == ["xinput1"]
        assert xp2_layers[4].tops == ["add1"]
        assert xp2_layers[5].bottoms == ["pool1", "conv2"]
        assert xp2_layers[5].tops == []
def conv2d_pool2d_nhwc_oihw_test(
    in_shape,
    w_shape,
    conv_padding,
    conv_strides,
    conv_dilation,
    pool_type,
    pool_size,
    pool_padding=[0, 0],
    pool_strides=[1, 1],
    conv_groups=1,
    conv_invalid=False,
    kernel_layout="OIHW",
    target="test-DPU",
):

    kernel_w, kernel_h = w_shape[2], w_shape[3]
    W = np.random.randint(-10, 10, size=w_shape).astype(np.float32)
    # B = np.array([1., -1.], dtype=np.float32)

    x1 = px.ops.input("in1", shape=list(in_shape))
    w1 = px.ops.constant("weight", W)
    conv1 = px.ops.conv2d(
        op_name="conv1",
        input_layer=x1,
        weights_layer=w1,
        kernel_size=[kernel_w, kernel_h],
        strides=list(conv_strides),
        padding_hw=list(conv_padding),
        dilation=list(conv_dilation),
        groups=conv_groups,
        data_layout="NHWC",
    )
    pool1 = px.ops.pool2d(
        op_name="pool1",
        input_layer=conv1,
        pool_type=pool_type, 
        pool_size=list(pool_size),
        padding=list(pool_padding),
        layout="NHWC",
    )
    net = [x1, conv1, pool1]
    xgraph = XGRAPH_FACTORY.build_from_xlayer(net)
    xgraph = px.partition(xgraph, [target])

    def inputs_func(iter):
        inputs = np.ones(in_shape, dtype=np.float32)
        return {'in1': inputs}

    quantizer = DECENTQuantizer(xgraph, inputs_func, work_dir=FILE_PATH)
    q_xgraph = quantizer.quantize()

    assert len(q_xgraph) == 3
    conv, pool = q_xgraph.get("conv1"), q_xgraph.get("pool1")

    if not conv_invalid:
        assert "vai_quant_weights" in conv.attrs
        assert "vai_quant_in" in conv.attrs
        assert "vai_quant_out" in conv.attrs
        assert "vai_quant" in conv.attrs
    
    assert "vai_quant_in" in pool.attrs
    assert "vai_quant_out" in pool.attrs
    assert "vai_quant" in pool.attrs

    remove_all_files_with_suffix(FILE_PATH, ".pb")
    remove_all_files_with_suffix(FILE_PATH, ".txt")
Exemple #30
0
def prequantize_onnx_model(onnx_model, target, inputs_func, out_file,
                           **kwargs):

    xgraph = _from_onnx(onnx_model)

    xgraph = px.partition(xgraph, [target])
    xgraph = px.optimize(xgraph, target)

    q_xgraph = px.quantize(xgraph, target, inputs_func, **kwargs)

    # Move quant_info information from XGraph to ONNX model
    tensor_quant_info = {}
    for X in q_xgraph.get_layers():
        if "vai_quant" in X.attrs and X.attrs["vai_quant"] != []:
            tensor_name = X.attrs['onnx_id']
            if tensor_name in tensor_quant_info:
                raise NotImplementedError("Quantization for ONNX tensor: {}"
                                          " already provided. Merging of"
                                          " multiple tensor quantization info"
                                          " parameters not supported yet")
            tensor_quant_info[tensor_name] = {
                "vai_quant": X.attrs["vai_quant"]
            }

            for vai_quant_elem in X.attrs['vai_quant']:
                tensor_quant_info[tensor_name][vai_quant_elem] = \
                    X.attrs[vai_quant_elem]

    for node in onnx_model.graph.node:
        node_w = NodeWrapper(node)
        tensor_name = node_w.get_outputs()[0]
        if tensor_name in tensor_quant_info:
            node_w.add_attribute(
                'vai_quant',
                list(tensor_quant_info[tensor_name]['vai_quant']),
                'STRINGS'
            )
            for vai_quant_elem in tensor_quant_info[tensor_name]['vai_quant']:
                node_w.add_attribute(
                    vai_quant_elem,
                    tensor_quant_info[tensor_name][vai_quant_elem],
                    'INTS'
                )

    # q_output = q_xgraph.get_quantizer_output()

    # for qkey in q_output.keys():
    #     quant_file = q_output.get_q_file(qkey)
    #     quant_info_file = q_output.get_q_info(qkey)
    #     quant_orig_pb = q_output.get_orig_pb(qkey)

    #     if not os.path.isfile(quant_info_file):
    #         raise ValueError("quant file: {} for qkey: {} does not exist"
    #                          .format(quant_info_file, qkey))

    #     meta = onnx_model.metadata_props.add()
    #     meta.key = "vitis_ai_quant--q_file--" + qkey
    #     meta.value = str(quant_file)

    #     meta = onnx_model.metadata_props.add()
    #     meta.key = "vitis_ai_quant--q_info--" + qkey
    #     meta.value = str(quant_info_file)

    #     meta = onnx_model.metadata_props.add()
    #     meta.key = "vitis_ai_quant--orig_pb--" + qkey
    #     meta.value = str(quant_orig_pb)

    onnx.save(onnx_model, out_file)