1 /* ----------------------------------------------------------------------
2  * Project:      CMSIS DSP Python Wrapper
3  * Title:        cmsismodule.h
4  * Description:  C code for the CMSIS-DSP Python wrapper
5  *
6  * $Date:        27 April 2021
7  * $Revision:    V1.0
8  *
9  * Target Processor: Cortex-M cores
10  * -------------------------------------------------------------------- */
11 /*
12  * Copyright (C) 2010-2021 ARM Limited or its affiliates. All rights reserved.
13  *
14  * SPDX-License-Identifier: Apache-2.0
15  *
16  * Licensed under the Apache License, Version 2.0 (the License); you may
17  * not use this file except in compliance with the License.
18  * You may obtain a copy of the License at
19  *
20  * www.apache.org/licenses/LICENSE-2.0
21  *
22  * Unless required by applicable law or agreed to in writing, software
23  * distributed under the License is distributed on an AS IS BASIS, WITHOUT
24  * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
25  * See the License for the specific language governing permissions and
26  * limitations under the License.
27  */
28 
29 #define MODNAME "cmsisdsp_svm"
30 #define MODINITNAME cmsisdsp_svm
31 
32 #include "cmsisdsp_module.h"
33 
34 
35 
36 NUMPYVECTORFROMBUFFER(f32,float32_t,NPY_FLOAT);
37 
38 
39 #define SVMTYPE(NAME)                       \
40 typedef struct {                            \
41     PyObject_HEAD                           \
42     arm_svm_##NAME##_instance_f32 *instance;\
43 } dsp_arm_svm_##NAME##_instance_f32Object;
44 
45 SVMTYPE(linear);
46 SVMTYPE(polynomial);
47 SVMTYPE(rbf);
48 SVMTYPE(sigmoid);
49 
50 #define SVMTYPEDEALLOC(NAME)                                                        \
51 static void                                                                         \
52 arm_svm_##NAME##_instance_f32_dealloc(dsp_arm_svm_##NAME##_instance_f32Object* self)\
53 {                                                                                   \
54     if (self->instance)                                                             \
55     {                                                                               \
56                                                                                     \
57        if (self->instance->dualCoefficients)                                        \
58        {                                                                            \
59           PyMem_Free((float32_t*)self->instance->dualCoefficients);                 \
60        }                                                                            \
61                                                                                     \
62        if (self->instance->supportVectors)                                          \
63        {                                                                            \
64           PyMem_Free((float32_t*)self->instance->supportVectors);                   \
65        }                                                                            \
66                                                                                     \
67        if (self->instance->classes)                                                 \
68        {                                                                            \
69           PyMem_Free((float32_t*)self->instance->classes);                          \
70        }                                                                            \
71                                                                                     \
72        PyMem_Free(self->instance);                                                  \
73     }                                                                               \
74                                                                                     \
75     Py_TYPE(self)->tp_free((PyObject*)self);                                        \
76 }
77 
78 SVMTYPEDEALLOC(linear);
79 SVMTYPEDEALLOC(polynomial);
80 SVMTYPEDEALLOC(rbf);
81 SVMTYPEDEALLOC(sigmoid);
82 
83 #define SVMTYPENEW(NAME)                                                             \
84 static PyObject *                                                                    \
85 arm_svm_##NAME##_instance_f32_new(PyTypeObject *type, PyObject *args, PyObject *kwds)\
86 {                                                                                    \
87     dsp_arm_svm_##NAME##_instance_f32Object *self;                                   \
88                                                                                      \
89     self = (dsp_arm_svm_##NAME##_instance_f32Object *)type->tp_alloc(type, 0);       \
90                                                                                      \
91     if (self != NULL) {                                                              \
92                                                                                      \
93         self->instance = PyMem_Malloc(sizeof(arm_svm_##NAME##_instance_f32));        \
94         self->instance->dualCoefficients=NULL;                                       \
95         self->instance->supportVectors=NULL;                                         \
96         self->instance->classes=NULL;                                                \
97                                                                                      \
98     }                                                                                \
99                                                                                      \
100                                                                                      \
101     return (PyObject *)self;                                                         \
102 }
103 
104 SVMTYPENEW(linear);
105 SVMTYPENEW(polynomial);
106 SVMTYPENEW(rbf);
107 SVMTYPENEW(sigmoid);
108 
109 /*
110 
111 LINEAR INIT
112 
113 */
114 
115 static int
arm_svm_linear_instance_f32_init(dsp_arm_svm_linear_instance_f32Object * self,PyObject * args,PyObject * kwds)116 arm_svm_linear_instance_f32_init(dsp_arm_svm_linear_instance_f32Object *self, PyObject *args, PyObject *kwds)
117 {
118 
119 PyObject *dualCoefficients=NULL;
120 PyObject *supportVectors=NULL;
121 PyObject *classes=NULL;
122 
123 char *kwlist[] = {
124 "nbOfSupportVectors",
125 "vectorDimension",
126 "intercept",
127 "dualCoefficients",
128 "supportVectors",
129 "classes",
130 NULL
131 };
132 
133 if (PyArg_ParseTupleAndKeywords(args, kwds, "|kkfOOO", kwlist,
134  &self->instance->nbOfSupportVectors
135 ,&self->instance->vectorDimension
136 ,&self->instance->intercept
137 ,&dualCoefficients
138 ,&supportVectors
139 ,&classes
140 ))
141     {
142 
143       INITARRAYFIELD(dualCoefficients,NPY_DOUBLE,double,float32_t);
144       INITARRAYFIELD(supportVectors,NPY_DOUBLE,double,float32_t);
145       INITARRAYFIELD(classes,NPY_INT32,int32_t,int32_t);
146     }
147     return 0;
148 }
149 
150 GETFIELD(arm_svm_linear_instance_f32,nbOfSupportVectors,"k");
151 GETFIELD(arm_svm_linear_instance_f32,vectorDimension,"k");
152 GETFIELD(arm_svm_linear_instance_f32,intercept,"f");
153 
154 
155 static PyMethodDef arm_svm_linear_instance_f32_methods[] = {
156 
157     {"nbOfSupportVectors", (PyCFunction) Method_arm_svm_linear_instance_f32_nbOfSupportVectors,METH_NOARGS,"nbOfSupportVectors"},
158     {"vectorDimension", (PyCFunction) Method_arm_svm_linear_instance_f32_vectorDimension,METH_NOARGS,"vectorDimension"},
159     {"intercept", (PyCFunction) Method_arm_svm_linear_instance_f32_intercept,METH_NOARGS,"intercept"},
160 
161     {NULL}  /* Sentinel */
162 };
163 
164 /*
165 
166 POLYNOMIAl INIT
167 
168 */
169 
170 static int
arm_svm_polynomial_instance_f32_init(dsp_arm_svm_polynomial_instance_f32Object * self,PyObject * args,PyObject * kwds)171 arm_svm_polynomial_instance_f32_init(dsp_arm_svm_polynomial_instance_f32Object *self, PyObject *args, PyObject *kwds)
172 {
173 
174 PyObject *dualCoefficients=NULL;
175 PyObject *supportVectors=NULL;
176 PyObject *classes=NULL;
177 
178 char *kwlist[] = {
179 "nbOfSupportVectors",
180 "vectorDimension",
181 "intercept",
182 "dualCoefficients",
183 "supportVectors",
184 "classes",
185 "degree",
186 "coef0",
187 "gamma",
188 NULL
189 };
190 
191 if (PyArg_ParseTupleAndKeywords(args, kwds, "|kkfOOOiff", kwlist,
192  &self->instance->nbOfSupportVectors
193 ,&self->instance->vectorDimension
194 ,&self->instance->intercept
195 ,&dualCoefficients
196 ,&supportVectors
197 ,&classes
198 ,&self->instance->degree
199 ,&self->instance->coef0
200 ,&self->instance->gamma
201 ))
202     {
203 
204       INITARRAYFIELD(dualCoefficients,NPY_DOUBLE,double,float32_t);
205       INITARRAYFIELD(supportVectors,NPY_DOUBLE,double,float32_t);
206       INITARRAYFIELD(classes,NPY_INT32,int32_t,int32_t);
207     }
208     return 0;
209 }
210 
211 GETFIELD(arm_svm_polynomial_instance_f32,nbOfSupportVectors,"k");
212 GETFIELD(arm_svm_polynomial_instance_f32,vectorDimension,"k");
213 GETFIELD(arm_svm_polynomial_instance_f32,intercept,"f");
214 GETFIELD(arm_svm_polynomial_instance_f32,degree,"i");
215 GETFIELD(arm_svm_polynomial_instance_f32,coef0,"f");
216 GETFIELD(arm_svm_polynomial_instance_f32,gamma,"f");
217 
218 
219 static PyMethodDef arm_svm_polynomial_instance_f32_methods[] = {
220 
221     {"nbOfSupportVectors", (PyCFunction) Method_arm_svm_polynomial_instance_f32_nbOfSupportVectors,METH_NOARGS,"nbOfSupportVectors"},
222     {"vectorDimension", (PyCFunction) Method_arm_svm_polynomial_instance_f32_vectorDimension,METH_NOARGS,"vectorDimension"},
223     {"intercept", (PyCFunction) Method_arm_svm_polynomial_instance_f32_intercept,METH_NOARGS,"intercept"},
224     {"degree", (PyCFunction) Method_arm_svm_polynomial_instance_f32_degree,METH_NOARGS,"degree"},
225     {"coef0", (PyCFunction) Method_arm_svm_polynomial_instance_f32_coef0,METH_NOARGS,"coef0"},
226     {"gamma", (PyCFunction) Method_arm_svm_polynomial_instance_f32_gamma,METH_NOARGS,"gamma"},
227 
228     {NULL}  /* Sentinel */
229 };
230 
231 /*
232 
233 RBF INIT
234 
235 */
236 
237 
238 static int
arm_svm_rbf_instance_f32_init(dsp_arm_svm_rbf_instance_f32Object * self,PyObject * args,PyObject * kwds)239 arm_svm_rbf_instance_f32_init(dsp_arm_svm_rbf_instance_f32Object *self, PyObject *args, PyObject *kwds)
240 {
241 
242 PyObject *dualCoefficients=NULL;
243 PyObject *supportVectors=NULL;
244 PyObject *classes=NULL;
245 
246 char *kwlist[] = {
247 "nbOfSupportVectors",
248 "vectorDimension",
249 "intercept",
250 "dualCoefficients",
251 "supportVectors",
252 "classes",
253 "gamma",
254 NULL
255 };
256 
257 if (PyArg_ParseTupleAndKeywords(args, kwds, "|kkfOOOf", kwlist,
258  &self->instance->nbOfSupportVectors
259 ,&self->instance->vectorDimension
260 ,&self->instance->intercept
261 ,&dualCoefficients
262 ,&supportVectors
263 ,&classes
264 ,&self->instance->gamma
265 ))
266     {
267 
268       INITARRAYFIELD(dualCoefficients,NPY_DOUBLE,double,float32_t);
269       INITARRAYFIELD(supportVectors,NPY_DOUBLE,double,float32_t);
270       INITARRAYFIELD(classes,NPY_INT32,int32_t,int32_t);
271     }
272     return 0;
273 }
274 
275 GETFIELD(arm_svm_rbf_instance_f32,nbOfSupportVectors,"k");
276 GETFIELD(arm_svm_rbf_instance_f32,vectorDimension,"k");
277 GETFIELD(arm_svm_rbf_instance_f32,intercept,"f");
278 GETFIELD(arm_svm_rbf_instance_f32,gamma,"f");
279 
280 
281 static PyMethodDef arm_svm_rbf_instance_f32_methods[] = {
282 
283     {"nbOfSupportVectors", (PyCFunction) Method_arm_svm_rbf_instance_f32_nbOfSupportVectors,METH_NOARGS,"nbOfSupportVectors"},
284     {"vectorDimension", (PyCFunction) Method_arm_svm_rbf_instance_f32_vectorDimension,METH_NOARGS,"vectorDimension"},
285     {"intercept", (PyCFunction) Method_arm_svm_rbf_instance_f32_intercept,METH_NOARGS,"intercept"},
286     {"gamma", (PyCFunction) Method_arm_svm_rbf_instance_f32_gamma,METH_NOARGS,"gamma"},
287 
288     {NULL}  /* Sentinel */
289 };
290 
291 /*
292 
293 SIGMOID INIT
294 
295 */
296 
297 static int
arm_svm_sigmoid_instance_f32_init(dsp_arm_svm_sigmoid_instance_f32Object * self,PyObject * args,PyObject * kwds)298 arm_svm_sigmoid_instance_f32_init(dsp_arm_svm_sigmoid_instance_f32Object *self, PyObject *args, PyObject *kwds)
299 {
300 
301 PyObject *dualCoefficients=NULL;
302 PyObject *supportVectors=NULL;
303 PyObject *classes=NULL;
304 
305 char *kwlist[] = {
306 "nbOfSupportVectors",
307 "vectorDimension",
308 "intercept",
309 "dualCoefficients",
310 "supportVectors",
311 "classes",
312 "coef0",
313 "gamma",
314 NULL
315 };
316 
317 if (PyArg_ParseTupleAndKeywords(args, kwds, "|kkfOOOff", kwlist,
318  &self->instance->nbOfSupportVectors
319 ,&self->instance->vectorDimension
320 ,&self->instance->intercept
321 ,&dualCoefficients
322 ,&supportVectors
323 ,&classes
324 ,&self->instance->coef0
325 ,&self->instance->gamma
326 ))
327     {
328 
329       INITARRAYFIELD(dualCoefficients,NPY_DOUBLE,double,float32_t);
330       INITARRAYFIELD(supportVectors,NPY_DOUBLE,double,float32_t);
331       INITARRAYFIELD(classes,NPY_INT32,int32_t,int32_t);
332     }
333     return 0;
334 }
335 
336 GETFIELD(arm_svm_sigmoid_instance_f32,nbOfSupportVectors,"k");
337 GETFIELD(arm_svm_sigmoid_instance_f32,vectorDimension,"k");
338 GETFIELD(arm_svm_sigmoid_instance_f32,intercept,"f");
339 GETFIELD(arm_svm_sigmoid_instance_f32,coef0,"f");
340 GETFIELD(arm_svm_sigmoid_instance_f32,gamma,"f");
341 
342 
343 static PyMethodDef arm_svm_sigmoid_instance_f32_methods[] = {
344 
345     {"nbOfSupportVectors", (PyCFunction) Method_arm_svm_sigmoid_instance_f32_nbOfSupportVectors,METH_NOARGS,"nbOfSupportVectors"},
346     {"vectorDimension", (PyCFunction) Method_arm_svm_sigmoid_instance_f32_vectorDimension,METH_NOARGS,"vectorDimension"},
347     {"intercept", (PyCFunction) Method_arm_svm_sigmoid_instance_f32_intercept,METH_NOARGS,"intercept"},
348     {"coef0", (PyCFunction) Method_arm_svm_sigmoid_instance_f32_coef0,METH_NOARGS,"coef0"},
349     {"gamma", (PyCFunction) Method_arm_svm_sigmoid_instance_f32_gamma,METH_NOARGS,"gamma"},
350 
351     {NULL}  /* Sentinel */
352 };
353 
354 DSPType(arm_svm_linear_instance_f32,arm_svm_linear_instance_f32_new,arm_svm_linear_instance_f32_dealloc,arm_svm_linear_instance_f32_init,arm_svm_linear_instance_f32_methods);
355 DSPType(arm_svm_polynomial_instance_f32,arm_svm_polynomial_instance_f32_new,arm_svm_polynomial_instance_f32_dealloc,arm_svm_polynomial_instance_f32_init,arm_svm_polynomial_instance_f32_methods);
356 DSPType(arm_svm_rbf_instance_f32,arm_svm_rbf_instance_f32_new,arm_svm_rbf_instance_f32_dealloc,arm_svm_rbf_instance_f32_init,arm_svm_rbf_instance_f32_methods);
357 DSPType(arm_svm_sigmoid_instance_f32,arm_svm_sigmoid_instance_f32_new,arm_svm_sigmoid_instance_f32_dealloc,arm_svm_sigmoid_instance_f32_init,arm_svm_sigmoid_instance_f32_methods);
358 
359 
360 
361 
typeRegistration(PyObject * module)362 void typeRegistration(PyObject *module) {
363 
364 
365 
366   ADDTYPE(arm_svm_linear_instance_f32);
367   ADDTYPE(arm_svm_polynomial_instance_f32);
368   ADDTYPE(arm_svm_rbf_instance_f32);
369   ADDTYPE(arm_svm_sigmoid_instance_f32);
370 
371 
372 }
373 
374 static PyObject *
cmsis_arm_svm_linear_init_f32(PyObject * obj,PyObject * args)375 cmsis_arm_svm_linear_init_f32(PyObject *obj, PyObject *args)
376 {
377 
378   PyObject *S=NULL; // input
379   uint16_t numTaps; // input
380   PyObject *pdualCoefficients=NULL; // input
381   float32_t *pdualCoefficients_converted=NULL; // input
382   PyObject *psupportVectors=NULL; // input
383   float32_t *psupportVectors_converted=NULL; // input
384   PyObject *pclasses=NULL; // input
385   int32_t *pclasses_converted=NULL; // input
386   uint32_t blockSize; // input
387 
388   uint32_t nbOfSupportVectors;
389   uint32_t vectorDimension;
390   float32_t intercept;
391 
392   if (PyArg_ParseTuple(args,"OkkfOOO",&S,
393     &nbOfSupportVectors,
394     &vectorDimension,
395     &intercept,
396     &pdualCoefficients,
397     &psupportVectors,
398     &pclasses
399     ))
400   {
401 
402     dsp_arm_svm_linear_instance_f32Object *selfS = (dsp_arm_svm_linear_instance_f32Object *)S;
403     GETARGUMENT(pdualCoefficients,NPY_DOUBLE,double,float32_t);
404     GETARGUMENT(psupportVectors,NPY_DOUBLE,double,float32_t);
405     GETARGUMENT(pclasses,NPY_INT32,int32_t,int32_t);
406 
407     arm_svm_linear_init_f32(selfS->instance,
408       nbOfSupportVectors,
409       vectorDimension,
410       intercept,
411       pdualCoefficients_converted,
412       psupportVectors_converted,
413       pclasses_converted);
414     Py_RETURN_NONE;
415 
416   }
417   return(NULL);
418 }
419 
420 static PyObject *
cmsis_arm_svm_polynomial_init_f32(PyObject * obj,PyObject * args)421 cmsis_arm_svm_polynomial_init_f32(PyObject *obj, PyObject *args)
422 {
423 
424   PyObject *S=NULL; // input
425   uint16_t numTaps; // input
426   PyObject *pdualCoefficients=NULL; // input
427   float32_t *pdualCoefficients_converted=NULL; // input
428   PyObject *psupportVectors=NULL; // input
429   float32_t *psupportVectors_converted=NULL; // input
430   PyObject *pclasses=NULL; // input
431   int32_t *pclasses_converted=NULL; // input
432   uint32_t blockSize; // input
433 
434   uint32_t nbOfSupportVectors;
435   uint32_t vectorDimension;
436   float32_t intercept;
437   int32_t         degree;
438   float32_t       coef0;
439   float32_t       gamma;
440 
441   if (PyArg_ParseTuple(args,"OkkfOOOiff",&S,
442     &nbOfSupportVectors,
443     &vectorDimension,
444     &intercept,
445     &pdualCoefficients,
446     &psupportVectors,
447     &pclasses,
448     &degree,
449     &coef0,
450     &gamma
451     ))
452   {
453 
454     dsp_arm_svm_polynomial_instance_f32Object *selfS = (dsp_arm_svm_polynomial_instance_f32Object *)S;
455     GETARGUMENT(pdualCoefficients,NPY_DOUBLE,double,float32_t);
456     GETARGUMENT(psupportVectors,NPY_DOUBLE,double,float32_t);
457     GETARGUMENT(pclasses,NPY_INT32,int32_t,int32_t);
458 
459     arm_svm_polynomial_init_f32(selfS->instance,
460       nbOfSupportVectors,
461       vectorDimension,
462       intercept,
463       pdualCoefficients_converted,
464       psupportVectors_converted,
465       pclasses_converted,
466       degree,
467       coef0,
468       gamma
469       );
470     Py_RETURN_NONE;
471 
472   }
473   return(NULL);
474 }
475 
476 static PyObject *
cmsis_arm_svm_rbf_init_f32(PyObject * obj,PyObject * args)477 cmsis_arm_svm_rbf_init_f32(PyObject *obj, PyObject *args)
478 {
479 
480   PyObject *S=NULL; // input
481   uint16_t numTaps; // input
482   PyObject *pdualCoefficients=NULL; // input
483   float32_t *pdualCoefficients_converted=NULL; // input
484   PyObject *psupportVectors=NULL; // input
485   float32_t *psupportVectors_converted=NULL; // input
486   PyObject *pclasses=NULL; // input
487   int32_t *pclasses_converted=NULL; // input
488   uint32_t blockSize; // input
489 
490   uint32_t nbOfSupportVectors;
491   uint32_t vectorDimension;
492   float32_t intercept;
493   float32_t       gamma;
494 
495   if (PyArg_ParseTuple(args,"OkkfOOOf",&S,
496     &nbOfSupportVectors,
497     &vectorDimension,
498     &intercept,
499     &pdualCoefficients,
500     &psupportVectors,
501     &pclasses,
502     &gamma
503     ))
504   {
505 
506     dsp_arm_svm_rbf_instance_f32Object *selfS = (dsp_arm_svm_rbf_instance_f32Object *)S;
507     GETARGUMENT(pdualCoefficients,NPY_DOUBLE,double,float32_t);
508     GETARGUMENT(psupportVectors,NPY_DOUBLE,double,float32_t);
509     GETARGUMENT(pclasses,NPY_INT32,int32_t,int32_t);
510 
511     arm_svm_rbf_init_f32(selfS->instance,
512       nbOfSupportVectors,
513       vectorDimension,
514       intercept,
515       pdualCoefficients_converted,
516       psupportVectors_converted,
517       pclasses_converted,
518       gamma
519       );
520     Py_RETURN_NONE;
521 
522   }
523   return(NULL);
524 }
525 
526 static PyObject *
cmsis_arm_svm_sigmoid_init_f32(PyObject * obj,PyObject * args)527 cmsis_arm_svm_sigmoid_init_f32(PyObject *obj, PyObject *args)
528 {
529 
530   PyObject *S=NULL; // input
531   uint16_t numTaps; // input
532   PyObject *pdualCoefficients=NULL; // input
533   float32_t *pdualCoefficients_converted=NULL; // input
534   PyObject *psupportVectors=NULL; // input
535   float32_t *psupportVectors_converted=NULL; // input
536   PyObject *pclasses=NULL; // input
537   int32_t *pclasses_converted=NULL; // input
538   uint32_t blockSize; // input
539 
540   uint32_t nbOfSupportVectors;
541   uint32_t vectorDimension;
542   float32_t intercept;
543   float32_t       coef0;
544   float32_t       gamma;
545 
546   if (PyArg_ParseTuple(args,"OkkfOOOff",&S,
547     &nbOfSupportVectors,
548     &vectorDimension,
549     &intercept,
550     &pdualCoefficients,
551     &psupportVectors,
552     &pclasses,
553     &coef0,
554     &gamma
555     ))
556   {
557 
558     dsp_arm_svm_sigmoid_instance_f32Object *selfS = (dsp_arm_svm_sigmoid_instance_f32Object *)S;
559     GETARGUMENT(pdualCoefficients,NPY_DOUBLE,double,float32_t);
560     GETARGUMENT(psupportVectors,NPY_DOUBLE,double,float32_t);
561     GETARGUMENT(pclasses,NPY_INT32,int32_t,int32_t);
562 
563     arm_svm_sigmoid_init_f32(selfS->instance,
564       nbOfSupportVectors,
565       vectorDimension,
566       intercept,
567       pdualCoefficients_converted,
568       psupportVectors_converted,
569       pclasses_converted,
570       coef0,
571       gamma
572       );
573     Py_RETURN_NONE;
574 
575   }
576   return(NULL);
577 }
578 
579 
580 #define SVMPREDICT(NAME)                                                                          \
581 static PyObject *                                                                                 \
582 cmsis_arm_svm_##NAME##_predict_f32(PyObject *obj, PyObject *args)                                 \
583 {                                                                                                 \
584                                                                                                   \
585   PyObject *S=NULL;                                                                               \
586   PyObject *pSrc=NULL;                                                                            \
587   float32_t *pSrc_converted=NULL;                                                                 \
588   int32_t dst;                                                                                    \
589   uint32_t blockSize;                                                                             \
590                                                                                                   \
591   if (PyArg_ParseTuple(args,"OO",&S,&pSrc))                                                       \
592   {                                                                                               \
593                                                                                                   \
594     dsp_arm_svm_##NAME##_instance_f32Object *selfS = (dsp_arm_svm_##NAME##_instance_f32Object *)S;\
595     GETARGUMENT(pSrc,NPY_DOUBLE,double,float32_t);                                                \
596                                                                                                   \
597                                                                                                   \
598                                                                                                   \
599     arm_svm_##NAME##_predict_f32(selfS->instance,pSrc_converted,&dst);                            \
600     PyObject* resultOBJ=Py_BuildValue("i",dst);                                                   \
601     PyObject *pythonResult = Py_BuildValue("O",resultOBJ);                                        \
602                                                                                                   \
603     FREEARGUMENT(pSrc_converted);                                                                 \
604     Py_DECREF(resultOBJ);                                                                         \
605     return(pythonResult);                                                                         \
606                                                                                                   \
607   }                                                                                               \
608   return(NULL);                                                                                   \
609 }
610 
611 SVMPREDICT(linear);
612 SVMPREDICT(polynomial);
613 SVMPREDICT(rbf);
614 SVMPREDICT(sigmoid);
615 
616 static PyMethodDef CMSISDSPMethods[] = {
617 
618 
619 {"arm_svm_linear_init_f32",  cmsis_arm_svm_linear_init_f32, METH_VARARGS,""},
620 {"arm_svm_linear_predict_f32",  cmsis_arm_svm_linear_predict_f32, METH_VARARGS,""},
621 
622 {"arm_svm_polynomial_init_f32",  cmsis_arm_svm_polynomial_init_f32, METH_VARARGS,""},
623 {"arm_svm_polynomial_predict_f32",  cmsis_arm_svm_polynomial_predict_f32, METH_VARARGS,""},
624 
625 {"arm_svm_rbf_init_f32",  cmsis_arm_svm_rbf_init_f32, METH_VARARGS,""},
626 {"arm_svm_rbf_predict_f32",  cmsis_arm_svm_rbf_predict_f32, METH_VARARGS,""},
627 
628 {"arm_svm_sigmoid_init_f32",  cmsis_arm_svm_sigmoid_init_f32, METH_VARARGS,""},
629 {"arm_svm_sigmoid_predict_f32",  cmsis_arm_svm_sigmoid_predict_f32, METH_VARARGS,""},
630 
631     {"error_out", (PyCFunction)error_out, METH_NOARGS, NULL},
632     {NULL, NULL, 0, NULL}        /* Sentinel */
633 };
634 
635 #ifdef IS_PY3K
cmsisdsp_traverse(PyObject * m,visitproc visit,void * arg)636 static int cmsisdsp_traverse(PyObject *m, visitproc visit, void *arg) {
637     Py_VISIT(GETSTATE(m)->error);
638     return 0;
639 }
640 
cmsisdsp_clear(PyObject * m)641 static int cmsisdsp_clear(PyObject *m) {
642     Py_CLEAR(GETSTATE(m)->error);
643     return 0;
644 }
645 
646 
647 static struct PyModuleDef moduledef = {
648         PyModuleDef_HEAD_INIT,
649         MODNAME,
650         NULL,
651         sizeof(struct module_state),
652         CMSISDSPMethods,
653         NULL,
654         cmsisdsp_traverse,
655         cmsisdsp_clear,
656         NULL
657 };
658 
659 #define INITERROR return NULL
660 
661 PyMODINIT_FUNC
CAT(PyInit_,MODINITNAME)662 CAT(PyInit_,MODINITNAME)(void)
663 
664 
665 #else
666 #define INITERROR return
667 
668 void CAT(init,MODINITNAME)(void)
669 #endif
670 {
671     import_array();
672 
673   #ifdef IS_PY3K
674     PyObject *module = PyModule_Create(&moduledef);
675   #else
676     PyObject *module = Py_InitModule(MODNAME, CMSISDSPMethods);
677   #endif
678 
679   if (module == NULL)
680       INITERROR;
681   struct module_state *st = GETSTATE(module);
682 
683   st->error = PyErr_NewException(MODNAME".Error", NULL, NULL);
684   if (st->error == NULL) {
685       Py_DECREF(module);
686       INITERROR;
687   }
688 
689 
690   typeRegistration(module);
691 
692   #ifdef IS_PY3K
693     return module;
694   #endif
695 }