def test_add_ext_same_key(self): ''' Modifier add_ext same key. ''' network = Network('test_net') network.add_ext('e0', InputLayer(3, 24)) with self.assertRaisesRegex(KeyError, 'Network: .*ext.*'): network.add_ext('e0', InputLayer(3, 24))
def test_init_ext(self): ''' Initial with external layers. ''' self.network.add_ext('e0', InputLayer(3, 224)) self.network.add_ext('e1', InputLayer(6, 224)) e0_layout = DataLayout(frngs=(FmapRange( (0, 0, 0, 0), FmapPosition(b=self.batch_size, n=self.network['e0'].nofm, h=self.network['e0'].hofm, w=self.network['e0'].wofm)), ), regions=self.input_layout.regions, parts=self.input_layout.parts) e1_layout = DataLayout(frngs=(FmapRange( (0, 0, 0, 0), FmapPosition(b=self.batch_size, n=self.network['e1'].nofm, h=self.network['e1'].hofm, w=self.network['e1'].wofm)), ), regions=self.input_layout.regions, parts=self.input_layout.parts) ext_layout_dict = {'e0': e0_layout, 'e1': e1_layout} df = NNDataflowScheme(self.network, self.input_layout, ext_layout_dict) self.assertIn('e0', df.ext_layout_dict) self.assertIn('e1', df.ext_layout_dict) self.assertEqual(df.ext_layout_dict['e0'], e0_layout) self.assertEqual(df.ext_layout_dict['e1'], e1_layout)
def test_data_loops(self): ''' Get data_loops. ''' dls = InputLayer.data_loops() ilayer = InputLayer(3, 227) self.assertTupleEqual(ilayer.data_loops(), dls) self.assertEqual(dls[de.FIL], DataDimLoops()) self.assertEqual(dls[de.IFM], DataDimLoops()) self.assertEqual(dls[de.OFM], DataDimLoops(le.OFM, le.BAT))
def test_ext_layers(self): ''' Get external layers. ''' self.assertTupleEqual(self.network.ext_layers(), tuple()) self.network.add_ext('e0', InputLayer(3, 224)) self.assertTupleEqual(self.network.ext_layers(), ('e0',)) self.network.add_ext('e1', InputLayer(3, 224)) self.assertTupleEqual(self.network.ext_layers(), ('e0', 'e1'))
def add_lstm_cell(network, name, size, xin, cin=None, hin=None): ''' Add a LSTM cell named `name` to the `network`, with the dimension `size`. `xin`, `cin`, `hin` are the layers' names whose outputs are x_t, C_{t-1}, h_{t-1}, respectively. Return the layers' names whose outputs are C_t, h_t. ''' from nn_dataflow.core import Network from nn_dataflow.core import InputLayer, FCLayer, EltwiseLayer if not isinstance(network, Network): raise TypeError('add_lstm_cell: network must be a Network instance.') if cin is None: cin = '{}_cinit'.format(name) network.add_ext(cin, InputLayer(size, 1)) if hin is None: hin = '{}_hinit'.format(name) network.add_ext(hin, InputLayer(size, 1)) if (cin not in network) or (hin not in network) or (xin not in network): raise ValueError('add_lstm_cell: cin {}, hin {}, xin {} must all be ' 'in the network.'.format(cin, hin, xin)) def gate_name(gate): ''' Name of a gate. ''' return '{}_{}gate'.format(name, gate) # Candidate. cand_name = '{}_cand'.format(name) prevs = (hin, xin) if hin else (xin, ) network.add(cand_name, FCLayer(len(prevs) * size, size), prevs=prevs) # Three gates. prevs = (hin, xin) if hin else (xin, ) for g in ['i', 'f', 'o']: network.add(gate_name(g), FCLayer(len(prevs) * size, size), prevs=prevs) # C_t. cout_name = '{}_cout'.format(name) cout_f_name = cout_name + '_f' prevs = (cin, gate_name('f')) if cin else (gate_name('f'), ) network.add(cout_f_name, EltwiseLayer(size, 1, len(prevs)), prevs=prevs) cout_i_name = cout_name + '_i' prevs = (cand_name, gate_name('i')) network.add(cout_i_name, EltwiseLayer(size, 1, 2), prevs=prevs) prevs = (cout_i_name, cout_f_name) network.add(cout_name, EltwiseLayer(size, 1, 2), prevs=prevs) # h_t. hout_name = '{}_hout'.format(name) prevs = (cout_name, gate_name('o')) network.add(hout_name, EltwiseLayer(size, 1, 2), prevs=prevs) return cout_name, hout_name
def test_init_invalid_eld_type(self): ''' Invalid ext_layout_dict value type. ''' self.network.add_ext('e0', InputLayer(3, 224)) self.network.add_ext('e1', InputLayer(3, 224)) with self.assertRaisesRegexp(TypeError, 'NNDataflowScheme: .*ext_layout*'): _ = NNDataflowScheme(self.network, self.input_layout, { 'e0': self.input_layout, 'e1': self.input_layout.frngs })
def setUp(self): self.alex_net = import_network('alex_net') self.vgg_net = import_network('vgg_net') net = Network('simple') net.set_input_layer(InputLayer(4, 2)) net.add('1', ConvLayer(4, 4, 2, 1)) net.add('2', ConvLayer(4, 4, 2, 1)) # Two more layers to avoid single-segment case. net.add('a1', ConvLayer(4, 1, 1, 1, strd=2)) net.add('a2', ConvLayer(1, 1, 1, 1)) self.simple_net = net net = Network('complex') net.set_input_layer(InputLayer(8, 8)) net.add('1', ConvLayer(8, 8, 8, 1)) net.add('2a', ConvLayer(8, 8, 8, 1), prevs=('1', )) net.add('3a', ConvLayer(8, 8, 8, 1)) net.add('2b', ConvLayer(8, 8, 8, 1), prevs=('1', )) net.add('3b', ConvLayer(8, 8, 8, 1)) net.add('4', ConvLayer(16, 8, 8, 1), prevs=('3a', '3b')) self.complex_net = net self.map_strategy = MapStrategyEyeriss self.resource = Resource( proc_region=NodeRegion(origin=PhyDim2(0, 0), dim=PhyDim2(1, 1), type=NodeRegion.PROC), dram_region=NodeRegion(origin=PhyDim2(0, 0), dim=PhyDim2(1, 1), type=NodeRegion.DRAM), src_data_region=NodeRegion(origin=PhyDim2(0, 0), dim=PhyDim2(1, 1), type=NodeRegion.DRAM), dst_data_region=NodeRegion(origin=PhyDim2(0, 0), dim=PhyDim2(1, 1), type=NodeRegion.DRAM), dim_array=PhyDim2(16, 16), size_gbuf=128 * 1024 // 2, # 128 kB size_regf=512 // 2, # 512 B array_bus_width=float('inf'), dram_bandwidth=float('inf'), no_time_mux=False, ) self.cost = Cost(mac_op=1, mem_hier=(200, 6, 2, 1), noc_hop=0, idl_unit=0) self.options = Option()
def test_repr(self): ''' __repr__. ''' # pylint: disable=eval-used for l in [ InputLayer(4, 12), InputLayer(4, [12, 24]), InputLayer(4, 12, strd=3), InputLayer(4, 12, strd=[3, 1]), InputLayer(4, [12, 24], strd=[3, 1]) ]: self.assertIn('InputLayer', repr(l)) self.assertEqual(eval(repr(l)), l)
def setUp(self): ''' Set up. ''' self.network = Network('test_net') self.network.set_input(InputLayer(3, 224)) self.network.add('c1', ConvLayer(3, 64, 224, 3)) self.network.add('p1', PoolingLayer(64, 7, 32)) self.network.add('f1', FCLayer(64, 1000, 7))
def test_add_unmatch_prev(self): ''' Modifier add unmatch prevs. ''' network = Network('test_net') network.set_input(InputLayer(3, 224)) network.add('c1', ConvLayer(3, 64, 224, 3)) with self.assertRaisesRegexp(ValueError, 'Network: .*c1.*p1.*mismatch fmap.*'): network.add('p1', PoolingLayer(64, 7, 2)) self.assertEqual(len(network), 1) with self.assertRaisesRegexp(ValueError, 'Network: .*c1.*c2.*mismatch fmap.*'): network.add('c2', ConvLayer(64, 128, 220, 3)) self.assertEqual(len(network), 1) with self.assertRaisesRegexp(ValueError, 'Network: .*merge.*c1.*p1.*'): network.add('p1', PoolingLayer(32, 7, 32)) self.assertEqual(len(network), 1) with self.assertRaisesRegexp(ValueError, 'Network: .*merge.*c1.*c2.*'): network.add('c2', ConvLayer(32, 128, 224, 3)) self.assertEqual(len(network), 1) network.add('c2', ConvLayer(64, 128, 224, 3)) with self.assertRaisesRegexp(ValueError, r'Network: .*merge.*c1\s*c2.*p1.*'): network.add('p1', PoolingLayer(128, 7, 32), prevs=('c1', 'c2')) self.assertEqual(len(network), 2)
def test_add_invalid_type(self): ''' Modifier add invalid type. ''' network = Network('test_net') network.set_input(InputLayer(3, 224)) with self.assertRaisesRegexp(TypeError, 'Network: .*Layer.*'): network.add('c1', (3, 64, 224, 3))
def test_add_same_key(self): ''' Modifier add same key. ''' network = Network('test_net') network.set_input(InputLayer(3, 224)) network.add('c1', ConvLayer(3, 64, 224, 3)) with self.assertRaisesRegexp(KeyError, 'Network: .*c1.*'): network.add('c1', ConvLayer(64, 128, 224, 3))
def test_add_no_prev(self): ''' Modifier add no prevs. ''' network = Network('test_net') network.set_input(InputLayer(3, 224)) network.add('c1', ConvLayer(3, 64, 224, 3)) with self.assertRaisesRegexp(KeyError, 'Network: .*prev.*p1.*'): network.add('p1', PoolingLayer(64, 7, 32), prevs='p1')
def test_add_ext(self): ''' Modifier add_ext. ''' self.assertEqual(len(self.network), 3) self.network.add_ext('e0', InputLayer(3, 24)) self.assertIsInstance(self.network['e0'], InputLayer) self.assertEqual(self.network['e0'].nofm, 3) self.assertEqual(self.network['e0'].hofm, 24) self.assertEqual(self.network['e0'].wofm, 24) self.network.add_ext('e1', InputLayer(5, (16, 20))) self.assertIsInstance(self.network['e1'], InputLayer) self.assertEqual(self.network['e1'].nofm, 5) self.assertEqual(self.network['e1'].hofm, 16) self.assertEqual(self.network['e1'].wofm, 20) self.assertEqual(len(self.network), 3)
def test_set_input(self): ''' Modifier set_input. ''' network = Network('test_net') network.set_input(InputLayer(3, 24)) self.assertIsInstance(network.input_layer(), InputLayer) self.assertEqual(network.input_layer().nofm, 3) self.assertEqual(network.input_layer().hofm, 24) self.assertEqual(network.input_layer().wofm, 24) self.assertEqual(len(network), 0)
def test_prevs_ext_next(self): ''' Get prevs next layer of an external layer. ''' self.network.add_ext('e0', InputLayer(3, 224)) self.network.add('n', ConvLayer(6, 3, 224, 1), prevs=(self.network.INPUT_LAYER_KEY, 'e0')) prevs = self.network.prevs('n') self.assertTupleEqual(prevs, (None, 'e0'))
def test_add_lstm_cell_not_in(self): ''' Add LSTM cell input not in. ''' net = Network('LSTM') net.set_input_layer(InputLayer(512, 1)) with self.assertRaisesRegex(ValueError, 'add_lstm_cell: .*in.*'): _ = nns.add_lstm_cell(net, 'cell0', 512, 'a', net.INPUT_LAYER_KEY, net.INPUT_LAYER_KEY) net = Network('LSTM') net.set_input_layer(InputLayer(512, 1)) with self.assertRaisesRegex(ValueError, 'add_lstm_cell: .*in.*'): _ = nns.add_lstm_cell(net, 'cell0', 512, net.INPUT_LAYER_KEY, 'a', net.INPUT_LAYER_KEY) net = Network('LSTM') net.set_input_layer(InputLayer(512, 1)) with self.assertRaisesRegex(ValueError, 'add_lstm_cell: .*in.*'): _ = nns.add_lstm_cell(net, 'cell0', 512, net.INPUT_LAYER_KEY, net.INPUT_LAYER_KEY, 'a')
def MLP_network(input_size, hiden_fc1, hiden_fc2, hiden_fc3, output_size): NN = Network('MLP_L') NN.set_input(InputLayer(input_size, 1)) NN.add('fc1', FCLayer(input_size, hiden_fc1)) NN.add('fc2', FCLayer(hiden_fc1, hiden_fc2)) NN.add('fc3', FCLayer(hiden_fc2, hiden_fc3)) NN.add('fc4', FCLayer(hiden_fc3, output_size)) return NN
def test_init_invalid_eld_keys(self): ''' Invalid ext_layout_dict keys. ''' with self.assertRaisesRegexp(ValueError, 'NNDataflowScheme: .*ext_layout_dict*'): _ = NNDataflowScheme(self.network, self.input_layout, {'e0': self.input_layout}) self.network.add_ext('e0', InputLayer(3, 224)) with self.assertRaisesRegexp(ValueError, 'NNDataflowScheme: .*ext_layout_dict*'): _ = NNDataflowScheme(self.network, self.input_layout)
def test_setitem_prev_input_ext(self): ''' __setitem__ previous is input or external. ''' df = NNDataflowScheme(self.network, self.input_layout) df['c1'] = self.c1res self.assertAlmostEqual(df.total_cost, self.c1res.total_cost) self.network.add_ext('e0', InputLayer(3, 224)) self.network.add('c2', self.network['c1'], prevs=('e0', )) df = NNDataflowScheme(self.network, self.input_layout, {'e0': self.input_layout}) df['c2'] = self.c1res self.assertAlmostEqual(df.total_cost, self.c1res.total_cost)
def test_iter(self): ''' Accessor iter. ''' num = 0 for layer in self.network: self.assertIn(layer, self.network) self.assertIsInstance(self.network[layer], Layer) num += 1 self.assertEqual(len(self.network), num) network = Network('test_net') network.set_input(InputLayer(3, 224)) with self.assertRaises(StopIteration): _ = next(iter(network))
def test_firsts_ext(self): ''' Get firsts with external layers. ''' self.network.add_ext('e0', InputLayer(3, 224)) self.network.add('c2', ConvLayer(3, 3, 224, 1), prevs=('e0',)) self.network.add('c3', ConvLayer(67, 3, 224, 1), prevs=('e0', 'c1')) self.network.add('c4', ConvLayer(6, 3, 224, 1), prevs=(self.network.INPUT_LAYER_KEY, 'e0',)) firsts = self.network.firsts() self.assertIn('c2', firsts) self.assertNotIn('c3', firsts) self.assertIn('c4', firsts)
def setUp(self): super(TestPipelineSegmentTiming, self).setUp() self.net1 = self.net['net1'] self.net4 = self.net['net4'] self.netlr = Network('net1') self.netlr.set_input_layer(InputLayer(10, 1)) self.netlr.add('0p1', PoolingLayer(10, 1, 1)) self.netlr.add('0p2', PoolingLayer(10, 1, 1)) self.netlr.add('0p3', PoolingLayer(10, 1, 1)) self.netlr.add('1', FCLayer(10, 20))
def test_add_lstm_cell(self): ''' Add LSTM cell. ''' net = Network('LSTM') net.set_input_layer(InputLayer(512, 1)) c, h = nns.add_lstm_cell(net, 'cell0', 512, net.INPUT_LAYER_KEY, net.INPUT_LAYER_KEY, net.INPUT_LAYER_KEY) c, h = nns.add_lstm_cell(net, 'cell1', 512, net.INPUT_LAYER_KEY, c, h) c, h = nns.add_lstm_cell(net, 'cell2', 512, net.INPUT_LAYER_KEY, c, h) num_weights = 0 for layer in net: try: num_weights += net[layer].total_filter_size() except AttributeError: pass self.assertEqual(num_weights, 512 * 512 * 2 * 4 * 3)
def setUp(self): self.network = Network('test_net') self.network.set_input(InputLayer(3, 224)) self.network.add('c1', ConvLayer(3, 64, 224, 3)) self.network.add('p1', PoolingLayer(64, 7, 32), prevs='c1') self.network.add('p2', PoolingLayer(64, 7, 32), prevs='c1') self.network.add('f1', FCLayer(64, 1000, 7), prevs=['p1', 'p2']) self.batch_size = 4 self.input_layout = partition.get_ofmap_layout( self.network.input_layer(), self.batch_size, PartitionScheme(order=range(pe.NUM), pdims=[(1, 1)] * pe.NUM), NodeRegion(origin=PhyDim2(0, 0), dim=PhyDim2(2, 1), type=NodeRegion.DATA)) self.c1res = SchedulingResult( dict_loop=OrderedDict([('cost', 1.), ('time', 2.), ('ops', 4.), ('access', [[7, 8, 9]] * me.NUM), ]), dict_part=OrderedDict([('cost', 0.5), ('total_nhops', [4, 5, 6]), ('num_nodes', 4), ]), ofmap_layout=partition.get_ofmap_layout( self.network['c1'], self.batch_size, PartitionScheme(order=range(pe.NUM), pdims=[(1, 1)] * pe.NUM), NodeRegion(origin=PhyDim2(0, 0), dim=PhyDim2(1, 2), type=NodeRegion.DATA))) self.pres = SchedulingResult( dict_loop=OrderedDict([('cost', 0.1), ('time', 0.05), ('ops', 0.1), ('access', [[.7, .8, .9]] * me.NUM), ]), dict_part=OrderedDict([('cost', 0.5), ('total_nhops', [.4, .5, .6]), ('num_nodes', 2), ]), ofmap_layout=partition.get_ofmap_layout( self.network['p1'], self.batch_size, PartitionScheme(order=range(pe.NUM), pdims=[(1, 1)] * pe.NUM), NodeRegion(origin=PhyDim2(0, 0), dim=PhyDim2(1, 2), type=NodeRegion.DATA))) self.dtfl = NNDataflowScheme(self.network, self.input_layout) self.dtfl['c1'] = self.c1res self.dtfl['p1'] = self.pres self.dtfl['p2'] = self.pres
def test_vertex_no_merge_lr(self): ''' LocalRegionLayer has no previous layer to merge with. ''' net = Network('tmp_net') net.set_input_layer(InputLayer(30, 1)) net.add('0', PoolingLayer(30, 1, 1)) net.add('1', FCLayer(30, 40)) net.add('1p', PoolingLayer(40, 1, 1)) ilp = self._make_ilp(net) for layer in net: vidx = ilp.dag_vertex_dict[layer] self.assertIn(layer, ilp.dag_vertex_list[vidx]) # Layer is named by topological order. self.assertTrue(layer.startswith(str(vidx)))
def test_len(self): ''' Accessor len. ''' self.assertEqual(len(self.network), 3) network = Network('test_net') self.assertEqual(len(network), 0) network.set_input(InputLayer(3, 224)) self.assertEqual(len(network), 0) network.add('c1', ConvLayer(3, 4, 224, 1)) self.assertEqual(len(network), 1) self.network.add('f2', FCLayer(64, 2000, 7), prevs='p1') self.assertEqual(len(self.network), 4) self.network.add('f3', FCLayer(3000, 1000), prevs=('f1', 'f2')) self.assertEqual(len(self.network), 5) self.network.add('f4', FCLayer(1000, 1000), prevs=('f1', 'f3')) self.assertEqual(len(self.network), 6)
def test_ext_layer(self): ''' With external layers. ''' network = self.alex_net network.add_ext('e0', InputLayer(4, 1)) network.add('l1', FCLayer(1000, 4)) network.add('l2', FCLayer(8, 4), prevs=('e0', 'l1')) batch_size = 16 options = Option(sw_gbuf_bypass=(True, True, True), sw_solve_loopblocking=True) nnd = NNDataflow(network, batch_size, self.resource, self.cost, self.map_strategy) tops, _ = nnd.schedule_search(options) self.assertTrue(tops)
You should have received a copy of the Modified BSD-3 License along with this program. If not, see <https://opensource.org/licenses/BSD-3-Clause>. """ from nn_dataflow.core import Network from nn_dataflow.core import InputLayer, ConvLayer, FCLayer, PoolingLayer ''' VGGNet-16 Simonyan and Zisserman, 2014 ''' NN = Network('VGG') NN.set_input_layer(InputLayer(3, 224)) NN.add('conv1', ConvLayer(3, 64, 224, 3)) NN.add('conv2', ConvLayer(64, 64, 224, 3)) NN.add('pool1', PoolingLayer(64, 112, 2)) NN.add('conv3', ConvLayer(64, 128, 112, 3)) NN.add('conv4', ConvLayer(128, 128, 112, 3)) NN.add('pool2', PoolingLayer(128, 56, 2)) NN.add('conv5', ConvLayer(128, 256, 56, 3)) NN.add('conv6', ConvLayer(256, 256, 56, 3)) NN.add('conv7', ConvLayer(256, 256, 56, 3)) NN.add('pool3', PoolingLayer(256, 28, 2)) NN.add('conv8', ConvLayer(256, 512, 28, 3))
Copyright (C) 2016-2020 by Tsinghua University and The Board of Trustees of Stanford University This program is free software: you can redistribute it and/or modify it under the terms of the Modified BSD-3 License as published by the Open Source Initiative. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the BSD-3 License for more details. You should have received a copy of the Modified BSD-3 License along with this program. If not, see <https://opensource.org/licenses/BSD-3-Clause>. """ from nn_dataflow.core import Network from nn_dataflow.core import InputLayer, FCLayer ''' MLP-S PRIME, 2016 ''' NN = Network('MLP-S') NN.set_input_layer(InputLayer(784, 1)) NN.add('fc1', FCLayer(784, 500)) NN.add('fc2', FCLayer(500, 250)) NN.add('fc3', FCLayer(250, 10))