using namespace std;
using namespace trinity_vision;
+static int avgp_rshamts[17] = {0,0,0,1,1,0,2,0,2,3,0,0,3,0,0,0,3};
+static int avgp_mults[17] = {0,0,1073741824,1431655765,1073741824,0,1431655765,0,1073741824,1908874354,0,0,1431655765,0,0,0,1073741824};
+
/** @brief a wrapper for TrinityCore/DataGen */
class TestdataGen: public TrinityCore<64>, public DataGen {
public:
/** input/output featuer map size */
conv1.data_size.OUT_H = 16;
conv1.data_size.OUT_W = 16;
- conv1.data_size.OUT_D = 64;
+ conv1.data_size.OUT_D = 64;
conv1.data_size.IN0_D = 64;
gen.append(conv1);
/** input/output featuer map size */
conv2.data_size.OUT_H = 16;
conv2.data_size.OUT_W = 16;
- conv2.data_size.OUT_D = 64;
+ conv2.data_size.OUT_D = 64;
conv2.data_size.IN0_D = 64;
gen.append(conv2);
/** input/output featuer map size */
conv.data_size.OUT_H = 16;
conv.data_size.OUT_W = 16;
- conv.data_size.OUT_D = 64;
+ conv.data_size.OUT_D = 64;
conv.data_size.IN0_D = 64;
gen.append(conv);
esum.cfg.FLT_W = 1;
esum.data_size.OUT_H = 16;
esum.data_size.OUT_W = 16;
- esum.data_size.OUT_D = 64;
+ esum.data_size.OUT_D = 64;
esum.data_size.IN0_D = 64;
esum.quant.IN0_MULT = 0x1 << 10;
esum.quant.IN1_MULT = 0x1 << 10;
gen.emit();
}
+/** @brief generate testdata for testcase3 (CONVE/ReLU/AVGP) */
+void gen_testdata_testcase3(const char* dir)
+{
+ TestdataGen gen(dir, 3);
+
+ /** 1) 3x3 CONVE */
+ TRINITY_CORE_PARA_OP conve;
+
+ conve.info.OPCODE = TRINITY_OPCODE_CONV;
+ conve.info.CNV_ESUM_EN = 1;
+ /** the number of code bits per weight */
+ conve.cfg.WGT_QBIT = 2;
+ /** the dimension of convoution filter */
+ conve.cfg.FLT_H = 3;
+ conve.cfg.FLT_W = 3;
+ /** the stride of convolution window */
+ conve.cfg.STR_Y = 2;
+ conve.cfg.STR_X = 2;
+ /** the amount of padding in pixels */
+ conve.cfg.PAD_L = 1;
+ conve.cfg.PAD_R = 1;
+ conve.cfg.PAD_T = 1;
+ conve.cfg.PAD_B = 1;
+ /** input/output featuer map size */
+ conve.data_size.OUT_H = 16;
+ conve.data_size.OUT_W = 16;
+ conve.data_size.OUT_D = 64;
+ conve.data_size.IN0_D = 64;
+ /** quantization */
+ conve.quant.IN1_ZERO = 6;
+ conve.quant.IN1_LSHAMT = 20;
+ conve.quant.IN1_RSHAMT = 0;
+ conve.quant.IN1_MULT = 0x400;
+
+ gen.append(conve);
+
+ /** 2) ReLU */
+ TRINITY_CORE_PARA_OP relu;
+
+ relu.info.OPCODE = TRINITY_OPCODE_RELU;
+ relu.cfg.WGT_QBIT = 1;
+ relu.cfg.FLT_H = 1;
+ relu.cfg.FLT_W = 1;
+ relu.data_size.OUT_H = 16;
+ relu.data_size.OUT_W = 16;
+ relu.data_size.OUT_D = 64;
+ relu.data_size.IN0_D = 64;
+ relu.quant.IN0_ZERO = 4;
+ relu.quant.OUT_ZERO = 4;
+
+ gen.append(relu);
+
+ /** 3) AVGP */
+ TRINITY_CORE_PARA_OP avgp;
+
+ avgp.info.OPCODE = TRINITY_OPCODE_AVGP;
+ avgp.cfg.WGT_QBIT = 1;
+ avgp.cfg.FLT_H = 2;
+ avgp.cfg.FLT_W = 2;
+ avgp.data_size.OUT_H = 15;
+ avgp.data_size.OUT_W = 15;
+ avgp.data_size.OUT_D = 64;
+ avgp.data_size.IN0_D = 64;
+ /** some fields have some assumed rules */
+ avgp.quant.IN0_ZERO = 0;
+ avgp.quant.OUT_ZERO = 0;
+ avgp.quant.OUT_LSHAMT = 0;
+ avgp.quant.OUT_RSHAMT = avgp_rshamts[avgp.cfg.FLT_H * avgp.cfg.FLT_W];
+ avgp.quant.OUT_MULT = avgp_mults[avgp.cfg.FLT_H * avgp.cfg.FLT_W];
+
+ gen.append(avgp);
+
+ gen.emit();
+}
+
/** @brief main function */
int main()
{
cout << "testcase2: CONV/ESUM/MAXP" << endl;
gen_testdata_testcase2("testcase2");
+ cout << "testcase3: CONVE/ReLU/AVGP" << endl;
+ gen_testdata_testcase3("testcase3");
+
/** @todo add more test cases for multi-layer models */
return 0;