1 /************************************************************************ 2 ************************************************************************ 3 Copyright (C) 2021 GRAME, Centre National de Creation Musicale 4 5 This program is free software; you can redistribute it and/or modify 6 it under the terms of the GNU Lesser General Public License as published by 7 the Free Software Foundation; either version 2.1 of the License, or 8 (at your option) any later version. 9 10 This program is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 GNU Lesser General Public License for more details. 14 15 You should have received a copy of the GNU Lesser General Public License 16 along with this program; if not, write to the Free Software 17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. 18 19 ************************************************************************ 20 ************************************************************************/ 21 22 #include <string> 23 #include <vector> 24 25 #ifndef LIBFAUSTCOMMON_H 26 #define LIBFAUSTCOMMON_H 27 28 /*! 29 \addtogroup boxcpp C++ interface for the Box API. 30 @{ 31 */ 32 33 /** 34 * Opaque types. 35 */ 36 class CTree; 37 typedef std::vector<CTree*> tvec; 38 39 enum SType { kSInt, kSReal }; 40 41 enum SOperator { kAdd, kSub, kMul, kDiv, kRem, kLsh, kARsh, kLRsh, kGT, kLT, kGE, kLE, kEQ, kNE, kAND, kOR, kXOR }; 42 43 /** 44 * Base class for factories. 45 */ 46 struct dsp_factory_base { 47 ~dsp_factory_basedsp_factory_base48 virtual ~dsp_factory_base() {} 49 50 virtual void write(std::ostream* out, bool binary = false, bool compact = false) {} 51 }; 52 53 #endif 54 55 #ifndef LIBFAUSTBOX_H 56 #define LIBFAUSTBOX_H 57 58 /** 59 * Opaque types. 60 */ 61 typedef CTree* Box; 62 63 /** 64 * Create global compilation context, has to be done first. 65 */ 66 extern "C" void createLibContext(); 67 68 /** 69 * Destroy global compilation context, has to be done last. 70 */ 71 extern "C" void destroyLibContext(); 72 73 /** 74 * Constant integer : for all t, x(t) = n. 75 * 76 * @param n - the integer 77 * 78 * @return the integer box. 79 */ 80 81 Box boxInt(int n); 82 83 /** 84 * Constant real : for all t, x(t) = n. 85 * 86 * @param n - the float/double value (depends of -single or -double compilation parameter) 87 * 88 * @return the float/double box. 89 */ 90 Box boxReal(double n); 91 92 /** 93 * The identity box, copy its input to its output. 94 * 95 * @return the identity box. 96 */ 97 Box boxWire(); 98 99 /** 100 * The cut box, to "stop"/terminate a signal. 101 * 102 * @return the cut box. 103 */ 104 Box boxCut(); 105 106 /** 107 * The sequential composition of two blocks (e.g., A:B) expects: outputs(A)=inputs(B) 108 * 109 * @return the seq box. 110 */ 111 Box boxSeq(Box x, Box y); 112 113 /** 114 * The parallel composition of two blocks (e.g., A,B). 115 * It places the two block-diagrams one on top of the other, without connections. 116 * 117 * @return the par box. 118 */ 119 Box boxPar(Box x, Box y); 120 121 Box boxPar3(Box x, Box y, Box z); 122 123 Box boxPar4(Box a, Box b, Box c, Box d); 124 125 Box boxPar5(Box a, Box b, Box c, Box d, Box e); 126 127 /** 128 * The split composition (e.g., A<:B) operator is used to distribute 129 * the outputs of A to the inputs of B. 130 * 131 * For the operation to be valid, the number of inputs of B 132 * must be a multiple of the number of outputs of A: outputs(A).k=inputs(B) 133 * 134 * @return the split box. 135 */ 136 Box boxSplit(Box x, Box y); 137 138 /** 139 * The merge composition (e.g., A:>B) is the dual of the split composition. 140 * 141 * The number of outputs of A must be a multiple of the number of inputs of B: outputs(A)=k.inputs(B) 142 * 143 * @return the merge box. 144 */ 145 Box boxMerge(Box x, Box y); 146 147 /** 148 * The recursive composition (e.g., A~B) is used to create cycles in the block-diagram 149 * in order to express recursive computations. 150 * It is the most complex operation in terms of connections: outputs(A)≥inputs(B) and inputs(A)≥outputs(B) 151 * 152 * @return the rec box. 153 */ 154 Box boxRec(Box x, Box y); 155 156 /** 157 * The route primitive facilitates the routing of signals in Faust. 158 * It has the following syntax: route(A,B,a,b,c,d,...) or route(A,B,(a,b),(c,d),...) 159 * 160 * @param n - the number of input signals 161 * @param m - the number of output signals 162 * @param r - the routing description, a 'par' expression of a,b / (a,b) input/output pairs 163 164 * @return the route box. 165 */ 166 Box boxRoute(Box n, Box m, Box r); 167 168 /** 169 * Create a delayed box. 170 * 171 * @return the delayed box. 172 */ 173 Box boxDelay(); 174 175 /** 176 * Create a delayed box. 177 * 178 * @param s - the box to be delayed 179 * @param del - the delay box that doesn't have to be fixed but must be bounded and cannot be negative 180 181 * @return the delayed box. 182 */ 183 Box boxDelay(Box s, Box del); 184 185 /** 186 * Create a casted box. 187 * 188 * @return the casted box. 189 */ 190 Box boxIntCast(); 191 192 /** 193 * Create a casted box. 194 * 195 * @param s - the box to be casted in integer 196 * 197 * @return the casted box. 198 */ 199 200 Box boxIntCast(Box s); 201 202 /** 203 * Create a casted box. 204 * 205 * @return the casted box. 206 */ 207 Box boxFloatCast(); 208 209 /** 210 * Create a casted box. 211 * 212 * @param s - the signal to be casted as float/double value (depends of -single or -double compilation parameter) 213 * 214 * @return the casted box. 215 */ 216 Box boxFloatCast(Box s); 217 218 /** 219 * Create a read only table. 220 * 221 * @return the table box. 222 */ 223 Box boxReadOnlyTable(); 224 225 /** 226 * Create a read only table. 227 * 228 * @param n - the table size, a constant numerical expression (see [1]) 229 * @param init - the table content 230 * @param ridx - the read index (an int between 0 and n-1) 231 * 232 * @return the table box. 233 */ 234 Box boxReadOnlyTable(Box n, Box init, Box ridx); 235 236 /** 237 * Create a read/write table. 238 * 239 * @return the table box. 240 */ 241 Box boxWriteReadTable(); 242 243 /** 244 * Create a read/write table. 245 * 246 * @param n - the table size, a constant numerical expression (see [1]) 247 * @param init - the table content 248 * @param widx - the write index (an integer between 0 and n-1) 249 * @param wsig - the input of the table 250 * @param ridx - the read index (an integer between 0 and n-1) 251 * 252 * @return the table box. 253 */ 254 Box boxWriteReadTable(Box n, Box init, Box widx, Box wsig, Box ridx); 255 256 /** 257 * Create a waveform. 258 * 259 * @param wf - the content of the waveform as a vector of boxInt or boxDouble boxes 260 * 261 * @return the waveform box. 262 */ 263 Box boxWaveform(const tvec& wf); 264 265 /** 266 * Create a soundfile block. 267 * 268 * @param label - of form "label[url:{'path1';'path2';'path3'}]" to describe a list of soundfiles 269 * @param chan - the number of outputs channels, a constant numerical expression (see [1]) 270 * 271 * @return the soundfile box. 272 */ 273 Box boxSoundfile(const std::string& label, Box chan); 274 275 /** 276 * Create a soundfile block. 277 * 278 * @param label - of form "label[url:{'path1';'path2';'path3'}]" to describe a list of soundfiles 279 * @param chan - the number of outputs channels, a constant numerical expression (see [1]) 280 * @param part - in the [0..255] range to select a given sound number, a constant numerical expression (see [1]) 281 * @param ridx - the read index (an integer between 0 and the selected sound length) 282 * 283 * @return the soundfile box. 284 */ 285 Box boxSoundfile(const std::string& label, Box chan, Box part, Box ridx); 286 287 /** 288 * Create a selector between two boxes. 289 * 290 * @return the selected box depending of the selector value at each time t. 291 */ 292 Box boxSelect2(); 293 294 /** 295 * Create a selector between two boxes. 296 * 297 * @param selector - when 0 at time t returns s1[t], otherwise returns s2[t] 298 * @param s1 - first box to be selected 299 * @param s2 - second box to be selected 300 * 301 * @return the selected box depending of the selector value at each time t. 302 */ 303 Box boxSelect2(Box selector, Box s1, Box s2); 304 305 /** 306 * Create a selector between three boxes. 307 * 308 * @return the selected box depending of the selector value at each time t. 309 */ 310 Box boxSelect3(); 311 312 /** 313 * Create a selector between three boxes. 314 * 315 * @param selector - when 0 at time t returns s1[t], when 1 at time t returns s2[t], otherwise returns s3[t] 316 * @param s1 - first box to be selected 317 * @param s2 - second box to be selected 318 * @param s3 - third signal to be selected 319 * 320 * @return the selected box depending of the selector value at each time t. 321 */ 322 Box boxSelect3(Box selector, Box s1, Box s2, Box s3); 323 324 /** 325 * Create a foreign constant box. 326 * 327 * @param type - the foreign constant type of SType 328 * @param name - the foreign constant name 329 * @param file - the include file where the foreign constant is defined 330 * 331 * @return the foreign constant box. 332 */ 333 Box boxFConst(SType type, const std::string& name, const std::string& file); 334 335 /** 336 * Create a foreign variable box. 337 * 338 * @param type - the foreign variable type of SType 339 * @param name - the foreign variable name 340 * @param file - the include file where the foreign variable is defined 341 * 342 * @return the foreign variable box. 343 */ 344 Box boxFVar(SType type, const std::string& name, const std::string& file); 345 346 /** 347 * Generic binary mathematical functions. 348 * 349 * @param op - the operator in SOperator set 350 * 351 * @return the result box of op(x,y). 352 */ 353 Box boxBinOp(SOperator op); 354 355 Box boxBinOp(SOperator op, Box b1, Box b2); 356 357 /** 358 * Specific binary mathematical functions. 359 * 360 * @return the result box. 361 */ 362 Box boxAdd(); 363 Box boxAdd(Box b1, Box b2); 364 Box boxSub(); 365 Box boxSub(Box b1, Box b2); 366 Box boxMul(); 367 Box boxMul(Box b1, Box b2); 368 Box boxDiv(); 369 Box boxDiv(Box b1, Box b2); 370 Box boxRem(); 371 Box boxRem(Box b1, Box b2); 372 373 Box boxLeftShift(); 374 Box boxLeftShift(Box b1, Box b2); 375 Box boxLRightShift(); 376 Box boxLRightShift(Box b1, Box b2); 377 Box boxARightShift(); 378 Box boxARightShift(Box b1, Box b2); 379 380 Box boxGT(); 381 Box boxGT(Box b1, Box b2); 382 Box boxLT(); 383 Box boxLT(Box b1, Box b2); 384 Box boxGE(); 385 Box boxGE(Box b1, Box b2); 386 Box boxLE(); 387 Box boxLE(Box b1, Box b2); 388 Box boxEQ(); 389 Box boxEQ(Box b1, Box b2); 390 Box boxNE(); 391 Box boxNE(Box b1, Box b2); 392 393 Box boxAND(); 394 Box boxAND(Box b1, Box b2); 395 Box boxOR(); 396 Box boxOR(Box b1, Box b2); 397 Box boxXOR(); 398 Box boxXOR(Box b1, Box b2); 399 400 /** 401 * Extended unary mathematical functions. 402 */ 403 404 Box boxAbs(); 405 Box boxAbs(Box x); 406 Box boxAcos(); 407 Box boxAcos(Box x); 408 Box boxTan(); 409 Box boxTan(Box x); 410 Box boxSqrt(); 411 Box boxSqrt(Box x); 412 Box boxSin(); 413 Box boxSin(Box x); 414 Box boxRint(); 415 Box boxRint(Box x); 416 Box boxLog(); 417 Box boxLog(Box x); 418 Box boxLog10(); 419 Box boxLog10(Box x); 420 Box boxFloor(); 421 Box boxFloor(Box x); 422 Box boxExp(); 423 Box boxExp(Box x); 424 Box boxExp10(); 425 Box boxExp10(Box x); 426 Box boxCos(); 427 Box boxCos(Box x); 428 Box boxCeil(); 429 Box boxCeil(Box x); 430 Box boxAtan(); 431 Box boxAtan(Box x); 432 Box boxAsin(); 433 Box boxAsin(Box x); 434 435 /** 436 * Extended binary mathematical functions. 437 */ 438 439 Box boxRemainder(); 440 Box boxRemainder(Box b1, Box b2); 441 Box boxPow(); 442 Box boxPow(Box b1, Box b2); 443 Box boxMin(); 444 Box boxMin(Box b1, Box b2); 445 Box boxMax(); 446 Box boxMax(Box b1, Box b2); 447 Box boxFmod(); 448 Box boxFmod(Box b1, Box b2); 449 Box boxAtan2(); 450 Box boxAtan2(Box b1, Box b2); 451 452 /** 453 * Create a button box. 454 * 455 * @param label - the label definition (see [2]) 456 * 457 * @return the button box. 458 */ 459 Box boxButton(const std::string& label); 460 461 /** 462 * Create a checkbox box. 463 * 464 * @param label - the label definition (see [2]) 465 * 466 * @return the checkbox box. 467 */ 468 Box boxCheckbox(const std::string& label); 469 470 /** 471 * Create a vertical slider box. 472 * 473 * @param label - the label definition (see [2]) 474 * @param init - the init box, a constant numerical expression (see [1]) 475 * @param min - the max box, a constant numerical expression (see [1]) 476 * @param max - the min box, a constant numerical expression (see [1]) 477 * @param step - the step box, a constant numerical expression (see [1]) 478 * 479 * @return the vertical slider box. 480 */ 481 Box boxVSlider(const std::string& label, Box init, Box min, Box max, Box step); 482 483 /** 484 * Create an horizontal slider box. 485 * 486 * @param label - the label definition (see [2]) 487 * @param init - the init box, a constant numerical expression (see [1]) 488 * @param min - the max box, a constant numerical expression (see [1]) 489 * @param max - the min box, a constant numerical expression (see [1]) 490 * @param step - the step box, a constant numerical expression (see [1]) 491 * 492 * @return the horizontal slider box. 493 */ 494 Box boxHSlider(const std::string& label, Box init, Box min, Box max, Box step); 495 496 /** 497 * Create a num entry box. 498 * 499 * @param label - the label definition (see [2]) 500 * @param init - the init box, a constant numerical expression (see [1]) 501 * @param min - the max box, a constant numerical expression (see [1]) 502 * @param max - the min box, a constant numerical expression (see [1]) 503 * @param step - the step box, a constant numerical expression (see [1]) 504 * 505 * @return the num entry box. 506 */ 507 Box boxNumEntry(const std::string& label, Box init, Box min, Box max, Box step); 508 509 /** 510 * Create a vertical bargraph box. 511 * 512 * @param label - the label definition (see [2]) 513 * @param min - the max box, a constant numerical expression (see [1]) 514 * @param max - the min box, a constant numerical expression (see [1]) 515 * 516 * @return the vertical bargraph box. 517 */ 518 Box boxVBargraph(const std::string& label, Box min, Box max); 519 520 /** 521 * Create a vertical bargraph box. 522 * 523 * @param label - the label definition (see [2]) 524 * @param min - the max box, a constant numerical expression (see [1]) 525 * @param max - the min box, a constant numerical expression (see [1]) 526 * @param s - the input box 527 * 528 * @return the vertical bargraph box. 529 */ 530 Box boxVBargraph(const std::string& label, Box min, Box max, Box x); 531 532 /** 533 * Create an horizontal bargraph box. 534 * 535 * @param label - the label definition (see [2]) 536 * @param min - the max box, a constant numerical expression (see [1]) 537 * @param max - the min box, a constant numerical expression (see [1]) 538 * 539 * @return the horizontal bargraph box. 540 */ 541 Box boxHBargraph(const std::string& label, Box min, Box max); 542 543 /** 544 * Create a horizontal bargraph box. 545 * 546 * @param label - the label definition (see [2]) 547 * @param min - the max box, a constant numerical expression (see [1]) 548 * @param max - the min box, a constant numerical expression (see [1]) 549 * @param s - the input box 550 * 551 * @return the vertical horizontal box. 552 */ 553 Box boxHBargraph(const std::string& label, Box min, Box max, Box x); 554 555 /** 556 * Create an attach box. 557 * 558 * The attach primitive takes two input boxes and produces one output box 559 * which is a copy of the first input. The role of attach is to force 560 * its second input boxes to be compiled with the first one. 561 * 562 * @return the attach box. 563 */ 564 Box boxAttach(); 565 566 /** 567 * Create an attach box. 568 * 569 * The attach primitive takes two input box and produces one output box 570 * which is a copy of the first input. The role of attach is to force 571 * its second input signal to be compiled with the first one. 572 * 573 * @param s1 - the first box 574 * @param s2 - the second box 575 * 576 * @return the attach signal. 577 */ 578 Box boxAttach(Box s1, Box s2); 579 580 /** 581 * Compile a box expression in a list of signals. 582 * 583 * @param box - the box expression 584 * @param error_msg - the error string to be filled 585 * 586 * @return a list of signals on success, otherwise an empty list. 587 */ 588 tvec boxesToSignals(Box box, std::string& error_msg); 589 590 /** 591 * Create a C++ Faust DSP factory from a box expression. 592 * 593 * @param name_app - the name of the Faust program 594 * @param box - the box expression 595 * @param argc - the number of parameters in argv array 596 * @param argv - the array of parameters 597 * @param error_msg - the error string to be filled 598 * 599 * @return a DSP factory on success, otherwise a null pointer. 600 */ 601 dsp_factory_base* createCPPDSPFactoryFromBoxes(const std::string& name_app, Box box, 602 int argc, const char* argv[], 603 std::string& error_msg); 604 605 /* 606 [1] Constant numerical expression : see https://faustdoc.grame.fr/manual/syntax/#constant-numerical-expressions 607 [2] Label definition : https://faustdoc.grame.fr/manual/syntax/#variable-parts-of-a-label 608 */ 609 610 /*! 611 @} 612 */ 613 614 #endif 615