1 /************************************************************************
3 IMPORTANT NOTE : this file contains two clearly delimited sections :
4 the ARCHITECTURE section (in two parts) and the USER section. Each section
5 is governed by its own copyright and license. Please check individually
6 each section for license and copyright information.
7 *************************************************************************/
9 /*******************BEGIN ARCHITECTURE SECTION (part 1/2)****************/
11 /************************************************************************
12 FAUST Architecture File
13 Copyright (C) 2010-2011 V. Lazzarini and GRAME
14 ---------------------------------------------------------------------
15 This Architecture section is free software; you can redistribute it
16 and/or modify it under the terms of the GNU General Public License
17 as published by the Free Software Foundation; either version 3 of
18 the License, or (at your option) any later version.
20 This program is distributed in the hope that it will be useful,
21 but WITHOUT ANY WARRANTY; without even the implied warranty of
22 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 GNU General Public License for more details.
25 You should have received a copy of the GNU General Public License
26 along with this program; If not, see <http://www.gnu.org/licenses/>.
28 EXCEPTION : As a special exception, you may create a larger work
29 that contains this FAUST architecture section and distribute
30 that work under terms of your choice, so long as this FAUST
31 architecture section is not modified.
34 ************************************************************************
35 ************************************************************************/
37 //==============================================================================
39 // CSOUND architecture file for FAUST
40 // Y. Orlarey & V. Lazzarini
42 // Usage : faust -uim -a csound.cpp <myfx>.dsp -o <myfx>.cpp
43 // g++ -O3 -DOPCODE_NAME=<myfx> -c <myfx>.cpp -o <myfx>.o
44 // ld -E --shared <myfx>.o -o <myfx>.so
47 // - 28/04/09 : first version
48 // - 29/04/09 : dynamic allocation
50 //==============================================================================
54 #include "csdl.h" /* CSOUND plugin API header */
56 // used to transform a symbol in a string
57 #define sym(name) xsym(name)
58 #define xsym(name) #name
60 // make sure we use csound floats
61 #define FAUSTFLOAT MYFLT
63 // we require macro declarations
64 #define FAUST_UIMACROS
66 // but we will ignore most of them
67 #define FAUST_ADDBUTTON(l,f)
68 #define FAUST_ADDCHECKBOX(l,f)
69 #define FAUST_ADDVERTICALSLIDER(l,f,i,a,b,s)
70 #define FAUST_ADDHORIZONTALSLIDER(l,f,i,a,b,s)
71 #define FAUST_ADDNUMENTRY(l,f,i,a,b,s)
72 #define FAUST_ADDVERTICALBARGRAPH(l,f,a,b)
73 #define FAUST_ADDHORIZONTALBARGRAPH(l,f,a,b)
75 #define max(x,y) (((x)>(y)) ? (x) : (y))
76 #define min(x,y) (((x)<(y)) ? (x) : (y))
80 // On Intel set FZ (Flush to Zero) and DAZ (Denormals Are Zero)
81 // flags to avoid costly denormals
83 #include <xmmintrin.h>
85 #define AVOIDDENORMALS _mm_setcsr(_mm_getcsr() | 0x8040)
87 #define AVOIDDENORMALS _mm_setcsr(_mm_getcsr() | 0x8000)
90 #define AVOIDDENORMALS
96 /******************************************************************************
97 *******************************************************************************
101 *******************************************************************************
102 *******************************************************************************/
110 * We will ignore metadata declarations
114 void declare (const char* key
, const char* value
) { }
118 * Abstract Definition of a user interface
128 virtual void addButton(const char* label
, FAUSTFLOAT
* zone
) = 0;
129 virtual void addToggleButton(const char* label
, FAUSTFLOAT
* zone
) = 0;
130 virtual void addCheckButton(const char* label
, FAUSTFLOAT
* zone
) = 0;
131 virtual void addVerticalSlider(const char* label
, FAUSTFLOAT
* zone
, FAUSTFLOAT init
, FAUSTFLOAT min
, FAUSTFLOAT max
, FAUSTFLOAT step
) = 0;
132 virtual void addHorizontalSlider(const char* label
, FAUSTFLOAT
* zone
, FAUSTFLOAT init
, FAUSTFLOAT min
, FAUSTFLOAT max
, FAUSTFLOAT step
) = 0;
133 virtual void addNumEntry(const char* label
, FAUSTFLOAT
* zone
, FAUSTFLOAT init
, FAUSTFLOAT min
, FAUSTFLOAT max
, FAUSTFLOAT step
) = 0;
135 // -- passive widgets
137 virtual void addNumDisplay(const char* label
, FAUSTFLOAT
* zone
, int precision
) {}
138 virtual void addTextDisplay(const char* label
, FAUSTFLOAT
* zone
, char* names
[], FAUSTFLOAT min
, FAUSTFLOAT max
) {}
139 virtual void addHorizontalBargraph(const char* label
, FAUSTFLOAT
* zone
, FAUSTFLOAT min
, FAUSTFLOAT max
) {}
140 virtual void addVerticalBargraph(const char* label
, FAUSTFLOAT
* zone
, FAUSTFLOAT min
, FAUSTFLOAT max
) {}
142 // -- widget's layouts
144 virtual void openFrameBox(const char* label
) {}
145 virtual void openTabBox(const char* label
) {}
146 virtual void openHorizontalBox(const char* label
) {}
147 virtual void openVerticalBox(const char* label
) {}
148 virtual void closeBox() {}
150 virtual void declare(FAUSTFLOAT
* zone
, const char* key
, const char* value
) {}
154 * A UI that simply collects the active zones in a vector
155 * and provides a method to copy the csound controls
157 class CSUI
: public UI
159 vector
<FAUSTFLOAT
*> vZone
;
164 virtual void addButton(const char* label
, FAUSTFLOAT
* zone
) { vZone
.push_back(zone
); }
165 virtual void addToggleButton(const char* label
, FAUSTFLOAT
* zone
) { vZone
.push_back(zone
); }
166 virtual void addCheckButton(const char* label
, FAUSTFLOAT
* zone
) { vZone
.push_back(zone
); }
167 virtual void addVerticalSlider(const char* label
, FAUSTFLOAT
* zone
, FAUSTFLOAT init
, FAUSTFLOAT min
, FAUSTFLOAT max
, FAUSTFLOAT step
) { vZone
.push_back(zone
); }
168 virtual void addHorizontalSlider(const char* label
, FAUSTFLOAT
* zone
, FAUSTFLOAT init
, FAUSTFLOAT min
, FAUSTFLOAT max
, FAUSTFLOAT step
) { vZone
.push_back(zone
); }
169 virtual void addNumEntry(const char* label
, FAUSTFLOAT
* zone
, FAUSTFLOAT init
, FAUSTFLOAT min
, FAUSTFLOAT max
, FAUSTFLOAT step
) { vZone
.push_back(zone
); }
171 void copyfrom(MYFLT
* mem
[]) {
172 for (unsigned int i
=0; i
<vZone
.size(); i
++) { *vZone
[i
] = *(mem
[i
]); }
175 int size() { return vZone
.size(); }
181 * Abstract Definition of a DSP
188 virtual int getNumInputs() = 0;
189 virtual int getNumOutputs() = 0;
190 virtual void instanceInit(int samplingFreq
) = 0;
191 virtual void init(int samplingFreq
)= 0;
192 virtual void buildUserInterface(UI
* interface
) = 0;
193 virtual void compute (int count
, FAUSTFLOAT
** input
, FAUSTFLOAT
** output
) = 0;
197 /********************END ARCHITECTURE SECTION (part 1/2)****************/
199 /**************************BEGIN USER SECTION **************************/
203 /***************************END USER SECTION ***************************/
205 /*******************BEGIN ARCHITECTURE SECTION (part 2/2)***************/
210 OPDS h
; /* basic attributes */
211 MYFLT
* aout
[FAUST_OUTPUTS
]; /* output buffers */
212 MYFLT
* ain
[FAUST_INPUTS
]; /* input buffers */
213 MYFLT
* ktl
[FAUST_ACTIVES
]; /* controls */
214 dsp
* DSP
; /* the Faust generated object */
215 CSUI
* interface
; /* do the mapping between CSound controls and DSP fields */
216 AUXCH dspmem
; /* aux memory allocated once to store the DSP object */
217 AUXCH intmem
; /* aux memory allocated once to store the interface object */
222 * Creates a "aaakkkk" CSound description string. Note that
223 * these string will never be released. Potential memory leak
225 static char* makeDescription(int numa
, int numk
=0)
227 char* str
= (char*)malloc(numa
+numk
+1); // NEED TO BE CHANGED ?
229 for (int i
=0; i
<numa
; i
++) str
[i
] = 'a';
230 for (int i
=0; i
<numk
; i
++) str
[numa
+i
] = 'k';
238 * CSOUND callback that allocates and initializes
239 * the FAUST generated DSP object and it's CSound interface
241 static int init(CSOUND
*csound
, dataspace
*p
)
243 if (p
->dspmem
.auxp
== NULL
)
244 csound
->AuxAlloc(csound
, sizeof(mydsp
), &p
->dspmem
);
246 if(p
->intmem
.auxp
== NULL
)
247 csound
->AuxAlloc(csound
, sizeof(CSUI
), &p
->intmem
);
250 p
->DSP
= new (p
->dspmem
.auxp
) mydsp
;
251 p
->interface
= new (p
->intmem
.auxp
) CSUI
;
253 if ((p
->DSP
== 0) | (p
->interface
== 0)) return NOTOK
;
255 p
->DSP
->init((int)csound
->GetSr(csound
));
256 p
->DSP
->buildUserInterface(p
->interface
);
263 * CSound callback that process the samples by updating
264 * the controls values and calling the compute() method
265 * of the DSP object. (Assume MYFLT = FAUSTFLOAT)
267 static int process32bits(CSOUND
*csound
, dataspace
*p
)
271 // update all the control values
272 p
->interface
->copyfrom(p
->ktl
);
274 p
->DSP
->compute(csound
->GetKsmps(csound
), p
->ain
, p
->aout
);
280 static OENTRY localops
[] = {
281 {(char*)sym(OPCODE_NAME
), sizeof(dataspace
),5,makeDescription(FAUST_OUTPUTS
), makeDescription(FAUST_INPUTS
,FAUST_ACTIVES
),
282 (SUBR
)init
, NULL
,(SUBR
)process32bits
}
288 /********************END ARCHITECTURE SECTION (part 2/2)****************/