1 /******************************************************************************/\r
2 /*!\r
3 * \file timlCNNAddConvLayer.c\r
4 */\r
5 /* Copyright (C) 2015 Texas Instruments Incorporated - http://www.ti.com/\r
6 *\r
7 * Redistribution and use in source and binary forms, with or without\r
8 * modification, are permitted provided that the following conditions\r
9 * are met:\r
10 *\r
11 * Redistributions of source code must retain the above copyright\r
12 * notice, this list of conditions and the following disclaimer.\r
13 *\r
14 * Redistributions in binary form must reproduce the above copyright\r
15 * notice, this list of conditions and the following disclaimer in the\r
16 * documentation and/or other materials provided with the\r
17 * distribution.\r
18 *\r
19 * Neither the name of Texas Instruments Incorporated nor the names of\r
20 * its contributors may be used to endorse or promote products derived\r
21 * from this software without specific prior written permission.\r
22 *\r
23 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\r
24 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\r
25 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\r
26 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT\r
27 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,\r
28 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT\r
29 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\r
30 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\r
31 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\r
32 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE\r
33 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\r
34 *\r
35 ******************************************************************************/\r
36 \r
37 \r
38 /*******************************************************************************\r
39 *\r
40 * INCLUDES\r
41 *\r
42 ******************************************************************************/\r
43 \r
44 #include "../api/timl.h"\r
45 \r
46 \r
47 /******************************************************************************/\r
48 /*!\r
49 * \ingroup cnn\r
50 * \brief Add conv layer\r
51 * \param[in,out] cnn CNN\r
52 * \param[in] kernelRow Kernel row size\r
53 * \param[in] kernelCol Kernel col size\r
54 * \param[in] strideX Kernel horizontal stride size\r
55 * \param[in] strideY Kernel vertical stride size\r
56 * \param[in] featureMapChannel Output feature map channel size\r
57 * \param[in] params Optional parameters\r
58 * \return Error code\r
59 */\r
60 /******************************************************************************/\r
61 \r
62 int timlCNNAddConvLayer(timlConvNeuralNetwork *cnn, int kernelRow, int kernelCol, int strideX, int strideY, int featureMapChannel, timlCNNConvParams params)\r
63 {\r
64 int err;\r
65 int prevFeatureMapRow;\r
66 int prevFeatureMapCol;\r
67 int prevFeatureMapChannel;\r
68 int currFeatureMapRow;\r
69 int currFeatureMapCol;\r
70 int padUp;\r
71 int padDown;\r
72 int padLeft;\r
73 int padRight;\r
74 timlCNNLayer *prev;\r
75 timlCNNLayer *convLayer;\r
76 \r
77 // init\r
78 err = 0;\r
79 prevFeatureMapRow = 0;\r
80 prevFeatureMapCol = 0;\r
81 prevFeatureMapChannel = 0;\r
82 currFeatureMapRow = 0;\r
83 currFeatureMapCol = 0;\r
84 prev = NULL;\r
85 convLayer = NULL;\r
86 padUp = params.padUp;\r
87 padDown = params.padDown;\r
88 padLeft = params.padLeft;\r
89 padRight = params.padRight;\r
90 \r
91 // params error checking\r
92 if (cnn == NULL) {\r
93 return ERROR_CNN_NULL_PTR;\r
94 }\r
95 if (cnn->tail == NULL) {\r
96 return ERROR_CNN_EMPTY;\r
97 }\r
98 if (kernelRow <= 0 || kernelCol <= 0) {\r
99 return ERROR_CNN_CONV_LAYER_KERNEL_SIZE;\r
100 }\r
101 if (padLeft >= kernelCol || padLeft < 0 || padRight >= kernelCol || padRight < 0 || padUp < 0 || padUp >= kernelRow || padDown >= kernelRow || padDown < 0) {\r
102 return ERROR_CNN_CONV_LAYER_PAD_SIZE;\r
103 }\r
104 if (strideX <= 0 || strideY <= 0) {\r
105 return ERROR_CNN_CONV_LAYER_STRIDE_SIZE;\r
106 }\r
107 if (featureMapChannel <= 0) {\r
108 return ERROR_CNN_FEATURE_MAP_CHANNEL;\r
109 }\r
110 \r
111 prev = cnn->tail;\r
112 prevFeatureMapRow = prev->row;\r
113 prevFeatureMapCol = prev->col;\r
114 prevFeatureMapChannel = prev->channel;\r
115 currFeatureMapRow = (prevFeatureMapRow - kernelRow + padUp + padDown)/strideY + 1;\r
116 currFeatureMapCol = (prevFeatureMapCol - kernelCol + padLeft + padRight)/strideX + 1;\r
117 if (currFeatureMapRow < 1 || currFeatureMapCol < 1) {\r
118 return ERROR_CNN_FEATURE_MAP_SIZE;\r
119 }\r
120 \r
121 // allocate conv layer\r
122 if (timlUtilMallocHost((void**)&convLayer, sizeof(timlCNNLayer))) {\r
123 return ERROR_CNN_LAYER_ALLOCATION;\r
124 }\r
125 \r
126 // load params\r
127 convLayer->convParams = params;\r
128 \r
129 // override params\r
130 convLayer->convParams.prevFeatureMapReshape = NULL;\r
131 convLayer->convParams.prevFeatureMapReshapeIndex = NULL;\r
132 convLayer->convParams.kernel = NULL;\r
133 convLayer->convParams.kernelInc = NULL;\r
134 convLayer->convParams.kernelGradAccum = NULL;\r
135 convLayer->convParams.bias = NULL;\r
136 convLayer->convParams.biasInc = NULL;\r
137 convLayer->convParams.biasGradAccum = NULL;\r
138 convLayer->convParams.connectivity = NULL;\r
139 convLayer->convParams.biasMultiplier = NULL;\r
140 convLayer->convParams.inputFeatureMapChannel = prevFeatureMapChannel;\r
141 convLayer->convParams.outputFeatureMapChannel = featureMapChannel;\r
142 convLayer->convParams.kernelRow = kernelRow;\r
143 convLayer->convParams.kernelCol = kernelCol;\r
144 convLayer->convParams.strideX = strideX;\r
145 convLayer->convParams.strideY = strideY;\r
146 convLayer->convParams.shared = false;\r
147 \r
148 // // set inactive params\r
149 // convLayer->inputParams = timlCNNInputParamsDefault();\r
150 // convLayer->poolingParams = timlCNNPoolingParamsDefault();\r
151 // convLayer->normParams = timlCNNNormParamsDefault();\r
152 // convLayer->linearParams = timlCNNLinearParamsDefault();\r
153 // convLayer->nonlinearParams = timlCNNNonlinearParamsDefault();\r
154 \r
155 convLayer->type = CNN_Conv;\r
156 convLayer->featureMap = NULL;\r
157 convLayer->delta = NULL;\r
158 convLayer->allocatorLevel = cnn->params.allocatorLevel;\r
159 convLayer->phase = cnn->params.phase;\r
160 convLayer->row = currFeatureMapRow;\r
161 convLayer->col = currFeatureMapCol;\r
162 convLayer->channel = featureMapChannel;\r
163 convLayer->batchSize = prev->batchSize;\r
164 convLayer->maxBatchSize = prev->maxBatchSize;\r
165 \r
166 // link the convLayer\r
167 convLayer->cnn = cnn;\r
168 convLayer->id = prev->id + 1;\r
169 convLayer->prev = prev;\r
170 convLayer->prev->next = convLayer;\r
171 convLayer->next = NULL;\r
172 cnn->tail = convLayer;\r
173 \r
174 return err;\r
175 \r
176 }\r