1
2 /*
3 # Sfront, a SAOL to C translator
4 # This file: Code generaton: core wavetables
5 #
6 # Copyright (c) 1999-2006, Regents of the University of California
7 # All rights reserved.
8 #
9 # Redistribution and use in source and binary forms, with or without
10 # modification, are permitted provided that the following conditions are
11 # met:
12 #
13 # Redistributions of source code must retain the above copyright
14 # notice, this list of conditions and the following disclaimer.
15 #
16 # Redistributions in binary form must reproduce the above copyright
17 # notice, this list of conditions and the following disclaimer in the
18 # documentation and/or other materials provided with the distribution.
19 #
20 # Neither the name of the University of California, Berkeley nor the
21 # names of its contributors may be used to endorse or promote products
22 # derived from this software without specific prior written permission.
23 #
24 # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
25 # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
26 # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
27 # A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
28 # OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
29 # SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
30 # LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
31 # DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
32 # THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
33 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
34 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
35 #
36 # Maintainer: John Lazzaro, lazzaro@cs.berkeley.edu
37 */
38
39
40 #include "tree.h"
41
42
43 /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
44 /* */
45 /* Top-level functions for wavetable logging and identification */
46 /* */
47 /*______________________________________________________________*/
48
49
50 /*********************************************************/
51 /* returns 1 if S_IDENT is a wavetable generator, else 0 */
52 /*********************************************************/
53
wavegeneratorname(tnode * ident)54 int wavegeneratorname(tnode * ident)
55
56 {
57
58 switch (ident->val[0]) {
59 case 'b':
60 if (!(strcmp(ident->val,"buzz")))
61 return 1;
62 return 0;
63 case 'c':
64 if (!(strcmp(ident->val,"concat")))
65 return 1;
66 if (!(strcmp(ident->val,"cubicseg")))
67 return 1;
68 return 0;
69 case 'd':
70 if (!(strcmp(ident->val,"data")))
71 return 1;
72 return 0;
73 case 'e':
74 if (!(strcmp(ident->val,"empty")))
75 return 1;
76 if (!(strcmp(ident->val,"expseg")))
77 return 1;
78 return 0;
79 case 'h':
80 if (!(strcmp(ident->val,"harm")))
81 return 1;
82 if (!(strcmp(ident->val,"harm_phase")))
83 return 1;
84 return 0;
85 case 'l':
86 if (!(strcmp(ident->val,"lineseg")))
87 return 1;
88 return 0;
89 case 'p':
90 if (!(strcmp(ident->val,"periodic")))
91 return 1;
92 if (!(strcmp(ident->val,"polynomial")))
93 return 1;
94 return 0;
95 case 'r':
96 if (!(strcmp(ident->val,"random")))
97 return 1;
98 return 0;
99 case 's':
100 if (!(strcmp(ident->val,"sample")))
101 return 1;
102 if (!(strcmp(ident->val,"spline")))
103 return 1;
104 if (!(strcmp(ident->val,"step")))
105 return 1;
106 return 0;
107 case 'w':
108 if (!(strcmp(ident->val,"window")))
109 return 1;
110 return 0;
111 }
112 return 0; /* will never happen */
113 }
114
115 /*********************************************************/
116 /* incremenets counter in has structure */
117 /*********************************************************/
118
haswavegenerator(tnode * ident)119 void haswavegenerator(tnode * ident)
120
121 {
122
123 switch (ident->val[0]) {
124 case 'b':
125 if (!(strcmp(ident->val,"buzz")))
126 {
127 has.w_buzz++;
128 return;
129 }
130 return;
131 case 'c':
132 if (!(strcmp(ident->val,"concat")))
133 {
134 has.w_concat++;
135 return;
136 }
137 if (!(strcmp(ident->val,"cubicseg")))
138 {
139 has.w_cubicseg++;
140 return;
141 }
142 return;
143 case 'd':
144 if (!(strcmp(ident->val,"data")))
145 {
146 has.w_data++;
147 return;
148 }
149 return;
150 case 'e':
151 if (!(strcmp(ident->val,"empty")))
152 {
153 has.w_empty++;
154 return;
155 }
156 if (!(strcmp(ident->val,"expseg")))
157 {
158 has.w_expseg++;
159 return;
160 }
161 return;
162 case 'h':
163 if (!(strcmp(ident->val,"harm")))
164 {
165 has.w_harm++;
166 return;
167 }
168 if (!(strcmp(ident->val,"harm_phase")))
169 {
170 has.w_harm_phase++;
171 return;
172 }
173 return;
174 case 'l':
175 if (!(strcmp(ident->val,"lineseg")))
176 {
177 has.w_lineseg++;
178 return;
179 }
180 return;
181 case 'p':
182 if (!(strcmp(ident->val,"periodic")))
183 {
184 has.w_periodic++;
185 return;
186 }
187 if (!(strcmp(ident->val,"polynomial")))
188 {
189 has.w_polynomial++;
190 return;
191 }
192 return;
193 case 'r':
194 if (!(strcmp(ident->val,"random")))
195 {
196 has.w_random++;
197 return;
198 }
199 return;
200 case 's':
201 if (!(strcmp(ident->val,"sample")))
202 {
203 has.w_sample++;
204 return;
205 }
206 if (!(strcmp(ident->val,"spline")))
207 {
208 has.w_spline++;
209 return;
210 }
211 if (!(strcmp(ident->val,"step")))
212 {
213 has.w_step++;
214 return;
215 }
216 return;
217 case 'w':
218 if (!(strcmp(ident->val,"window")))
219 {
220 has.w_window++;
221 return;
222 }
223 return;
224 default:
225 return;
226 }
227 }
228
229 /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
230 /* */
231 /* Top-level functions for wavetable code generation. */
232 /* */
233 /*______________________________________________________________*/
234
235 extern char * makewstring(char *);
236
237 /*********************************************************/
238 /* declares local variables for table generators */
239 /* */
240 /* modes values: */
241 /* */
242 /* S_SASLFILE: SASL table commands (readscore.c) */
243 /* S_OPCODE : opcode tables (writeop.c) */
244 /* S_INSTR : instr tables (writeorc.c) */
245 /* S_GLOBAL : global tables (writeorc.c) */
246 /* */
247 /*********************************************************/
248
wavegeneratorvar(sigsym * sptr)249 void wavegeneratorvar(sigsym * sptr)
250
251 {
252 tnode * wname = sptr->defnode->down->next;
253 tnode * ident = sptr->defnode->down->next->next->next;
254 tnode * tptr = sptr->defnode->down->next->next->next->next->next->down;
255 sampleinfo * sinfo;
256 int i,j;
257 int lc = 0;
258 char * lname = makewstring(wname->val);
259
260 /* no variables declarations needed for constant tables */
261
262 if ((sptr->defnode->vol == CONSTANT) && (sptr->defnode->usesinput))
263 return;
264
265 if (tptr == NULL)
266 {
267 printf("Error: Generator needs size parameter.\n");
268 showerrorplace(sptr->defnode->down->linenum,
269 sptr->defnode->down->filename);
270 }
271
272 z[lc++] = "int %2$s_size;";
273 z[lc++] = "float %2$s_rounding;";
274 tptr = tptr->next;
275 if (tptr != NULL)
276 tptr = tptr->next;
277
278 switch (ident->val[0]) {
279 case 'b':
280 if (!(strcmp(ident->val,"buzz")))
281 {
282 z[lc++]="float %2$s_scale;";
283 z[lc++]="float %2$s_base;";
284 z[lc++]="float %2$s_index;";
285 z[lc++]="float %2$s_acc;";
286 i = 1;
287 while (tptr != NULL)
288 {
289 if (tptr->ttype == S_EXPR)
290 {
291 switch (i) {
292 case 1:
293 z[lc++]="int %2$s_nharm;";
294 break;
295 case 2:
296 z[lc++]="int %2$s_lowharm;";
297 break;
298 case 3:
299 z[lc++]="float %2$s_rolloff;";
300 break;
301 default:
302 printf("Error: Too many parameters for buzz generator.\n");
303 showerrorplace(sptr->defnode->down->linenum,
304 sptr->defnode->down->filename);
305 }
306 i++;
307 }
308 tptr = tptr->next;
309 }
310 if (i<4)
311 {
312 printf("Error: Too few parameters for buzz generator.\n");
313 showerrorplace(sptr->defnode->down->linenum,
314 sptr->defnode->down->filename);
315 }
316 printwavesymblock2(lc, wname);
317 break;
318 }
319 break;
320 case 'c':
321 if (!(strcmp(ident->val,"concat")))
322 {
323 i = 1;
324 while (tptr != NULL)
325 {
326 if (tptr->ttype == S_EXPR)
327 {
328 mz(lc); sprintf(z[lc++],"int %s_ft%i;",lname,i);
329 i++;
330 }
331 tptr = tptr->next;
332 }
333 printwavesymblock2(lc, wname);
334 break;
335 }
336 if (!(strcmp(ident->val,"cubicseg")))
337 {
338 i = 1; j = 0;
339 z[lc++]="float %2$s_xf;";
340 z[lc++]="float %2$s_Q;";
341 z[lc++]="float %2$s_R;";
342 z[lc++]="float %2$s_S;";
343 z[lc++]="float %2$s_T;";
344 while (tptr != NULL)
345 {
346 if (tptr->ttype == S_EXPR)
347 {
348 switch (j) {
349 case 0:
350 mz(lc); sprintf(z[lc++],"float %s_infl%i;",lname,i);
351 mz(lc); sprintf(z[lc++],"float %s_a%i;",lname,i);
352 mz(lc); sprintf(z[lc++],"float %s_b%i;",lname,i);
353 mz(lc); sprintf(z[lc++],"float %s_c%i;",lname,i);
354 mz(lc); sprintf(z[lc++],"float %s_d%i;",lname,i);
355 break;
356 case 1:
357 mz(lc); sprintf(z[lc++],"float %s_y%i;",lname, 2*i-1);
358 break;
359 case 2:
360 mz(lc); sprintf(z[lc++],"float %s_x%i;",lname,i);
361 break;
362 case 3:
363 mz(lc); sprintf(z[lc++],"float %s_y%i;",lname, 2*i);
364 break;
365 }
366 j++;
367 if (j == 4)
368 {
369 j = 0; i++;
370 }
371 }
372 tptr = tptr->next;
373 }
374
375 /* for correct compilation for 'not enough x' error condition */
376
377 mz(lc);
378 if (j != 0)
379 i++;
380 sprintf(z[lc++],"float %s_infl%i;",lname,i);
381
382 printwavesymblock2(lc, wname);
383 break;
384 }
385 break;
386 case 'd':
387 if (!(strcmp(ident->val,"data")))
388 {
389 i = 1;
390 while (tptr != NULL)
391 {
392 if (tptr->ttype == S_EXPR)
393 {
394 mz(lc); sprintf(z[lc++],"float %s_p%i;",lname,i);
395 i++;
396 }
397 tptr = tptr->next;
398 }
399 printwavesymblock2(lc, wname);
400 break;
401 }
402 break;
403 case 'e':
404 if (!(strcmp(ident->val,"empty")))
405 {
406 if (tptr != NULL)
407 {
408 printf("Error: Too many parameters for empty generator.\n");
409 showerrorplace(sptr->defnode->down->linenum,
410 sptr->defnode->down->filename);
411 }
412 printwavesymblock2(lc, wname);
413 break;
414 }
415 if (!(strcmp(ident->val,"expseg")))
416 {
417 i = 1;
418 while (tptr != NULL)
419 {
420 if (tptr->ttype == S_EXPR)
421 {
422 if ((i % 2) == 1)
423 {
424 mz(lc); sprintf(z[lc++],"float %s_x%i;",lname,(i/2)+1);
425 mz(lc); sprintf(z[lc++],"float %s_d%i;",lname,(i/2)+1);
426 mz(lc); sprintf(z[lc++],"float %s_e%i;",lname,(i/2)+1);
427 }
428 else
429 {
430 mz(lc); sprintf(z[lc++],"float %s_y%i;",lname,(i/2));
431 }
432 i++;
433 }
434 tptr = tptr->next;
435 }
436 if ((i % 2) == 0)
437 {
438 mz(lc); sprintf(z[lc++],"float %s_y%i;",lname,(i/2));
439 }
440 printwavesymblock2(lc, wname);
441 break;
442 }
443 break;
444 case 'h':
445 if (!(strcmp(ident->val,"harm")))
446 {
447 z[lc++]="float %2$s_base;";
448 z[lc++]="float %2$s_index;";
449 i = 1;
450 while (tptr != NULL)
451 {
452 if (tptr->ttype == S_EXPR)
453 {
454 mz(lc); sprintf(z[lc++],"float %s_f%i;",lname,i);
455 i++;
456 }
457 tptr = tptr->next;
458 }
459 printwavesymblock2(lc, wname);
460 break;
461 }
462 if (!(strcmp(ident->val,"harm_phase")))
463 {
464 z[lc++]="float %2$s_base;";
465 z[lc++]="float %2$s_index;";
466 i = 1;
467 while (tptr != NULL)
468 {
469 if (tptr->ttype == S_EXPR)
470 {
471 if ((i % 2) == 1)
472 {
473 mz(lc); sprintf(z[lc++],"float %s_f%i;",lname,(i/2)+1);
474 }
475 else
476 {
477 mz(lc); sprintf(z[lc++],"float %s_ph%i;",lname,(i/2));
478 }
479 i++;
480 }
481 tptr = tptr->next;
482 }
483 if ((i % 2) == 0)
484 {
485 printf("Error: F parameter w/o a ph in harm_phase generator.\n");
486 showerrorplace(sptr->defnode->down->linenum,
487 sptr->defnode->down->filename);
488 }
489 printwavesymblock2(lc, wname);
490 break;
491 }
492 break;
493 case 'l':
494 if (!(strcmp(ident->val,"lineseg")))
495 {
496 i = 1;
497 while (tptr != NULL)
498 {
499 if (tptr->ttype == S_EXPR)
500 {
501 if ((i % 2) == 1)
502 {
503 mz(lc); sprintf(z[lc++],"float %s_x%i;",lname,(i/2)+1);
504 mz(lc); sprintf(z[lc++],"float %s_d%i;",lname,(i/2)+1);
505 }
506 else
507 {
508 mz(lc); sprintf(z[lc++],"float %s_y%i;",lname,(i/2));
509 }
510 i++;
511 }
512 tptr = tptr->next;
513 }
514 if ((i % 2) == 0)
515 {
516 mz(lc); sprintf(z[lc++],"float %s_y%i;",lname,(i/2));
517 }
518 printwavesymblock2(lc, wname);
519 break;
520 }
521 break;
522 case 'p':
523 if (!(strcmp(ident->val,"periodic")))
524 {
525 z[lc++]="float %2$s_base;";
526 z[lc++]="float %2$s_index;";
527 i = 1;
528 while (tptr != NULL)
529 {
530 if (tptr->ttype == S_EXPR)
531 {
532 switch(i % 3) {
533 case 1:
534 mz(lc); sprintf(z[lc++],"float %s_p%i;",lname,(i/3)+1);
535 break;
536 case 2:
537 mz(lc); sprintf(z[lc++],"float %s_f%i;",lname,(i/3)+1);
538 break;
539 case 0:
540 mz(lc); sprintf(z[lc++],"float %s_ph%i;",lname,(i/3));
541 break;
542 }
543 i++;
544 }
545 tptr = tptr->next;
546 }
547 if ((i % 3) != 1)
548 {
549 printf("Error: Incomplete data triplet in periodic generator.\n");
550 showerrorplace(sptr->defnode->down->linenum,
551 sptr->defnode->down->filename);
552 }
553 printwavesymblock2(lc, wname);
554 break;
555 }
556 if (!(strcmp(ident->val,"polynomial")))
557 {
558 i = 1;
559 z[lc++]="float %2$s_scale;";
560 z[lc++]="float %2$s_index;";
561 z[lc++]="float %2$s_acc;";
562 while (tptr != NULL)
563 {
564 if (tptr->ttype == S_EXPR)
565 {
566 switch (i) {
567 case 1:
568 z[lc++]="float %2$s_xmin;";
569 break;
570 case 2:
571 z[lc++]="float %2$s_xmax;";
572 break;
573 default:
574 mz(lc); sprintf(z[lc++],"float %s_a%i;",lname,i-3);
575 break;
576 }
577 i++;
578 }
579 tptr = tptr->next;
580 }
581 printwavesymblock2(lc, wname);
582 break;
583 }
584 break;
585 case 'r':
586 if (!(strcmp(ident->val,"random")))
587 {
588 i = 1;
589 z[lc++]="float %2$s_c1;";
590 z[lc++]="float %2$s_x;";
591 z[lc++]="float %2$s_y;";
592 while (tptr != NULL)
593 {
594 if (tptr->ttype == S_EXPR)
595 {
596 switch (i) {
597 case 1:
598 z[lc++]="int %2$s_dist;";
599 break;
600 case 2:
601 z[lc++]="float %2$s_p1;";
602 break;
603 case 3:
604 z[lc++]="float %2$s_p2;";
605 break;
606 default:
607 printf("Error: Too many parameters for random generator.\n");
608 showerrorplace(sptr->defnode->down->linenum,
609 sptr->defnode->down->filename);
610 }
611 i++;
612 }
613 tptr = tptr->next;
614 }
615 if (i<3)
616 {
617 printf("Error: Insufficient parameters for random generator.\n");
618 showerrorplace(sptr->defnode->down->linenum,
619 sptr->defnode->down->filename);
620 }
621 printwavesymblock2(lc, wname);
622 break;
623 }
624 break;
625 case 's':
626 if (!(strcmp(ident->val,"sample")))
627 {
628 z[lc++]="int %2$s_skip;";
629
630 sinfo = (sampleinfo *)
631 sptr->defnode->down->next->next->next->next->next->down->next->next->ibus;
632
633 mz(lc);
634 sprintf(z[lc++],"unsigned char %s_c[%i];",lname, sinfo->framebytes);
635
636 printwavesymblock2(lc, wname);
637 break;
638 }
639 if (!(strcmp(ident->val,"spline")))
640 {
641 z[lc++]="float %2$s_xf;";
642 z[lc++]="float %2$s_Q;";
643 z[lc++]="float %2$s_R;";
644 z[lc++]="float %2$s_S;";
645 z[lc++]="float %2$s_x1;";
646 z[lc++]="float %2$s_y1;";
647 z[lc++]="float %2$s_k1;";
648 i = 1;
649 while (tptr != NULL)
650 {
651 if (tptr->ttype == S_EXPR)
652 {
653 if (!(i % 3))
654 {
655 mz(lc);
656 sprintf(z[lc++],"float %s_y%i;",lname,(i/3)+1);
657 mz(lc);
658 sprintf(z[lc++],"float %s_x%i;",lname,(i/3)+1);
659 mz(lc);
660 sprintf(z[lc++],"float %s_k%i;",lname,(i/3)+1);
661 mz(lc);
662 sprintf(z[lc++],"float %s_a%i;",lname,(i/3));
663 mz(lc);
664 sprintf(z[lc++],"float %s_b%i;",lname,(i/3));
665 mz(lc);
666 sprintf(z[lc++],"float %s_c%i;",lname,(i/3));
667 mz(lc);
668 sprintf(z[lc++],"float %s_d%i;",lname,(i/3));
669 }
670 i++;
671 }
672 tptr = tptr->next;
673 }
674 printwavesymblock2(lc, wname);
675 break;
676 }
677 if (!(strcmp(ident->val,"step")))
678 {
679 i = 1;
680 z[lc++]="float %2$s_x1;";
681 while (tptr != NULL)
682 {
683 if (tptr->ttype == S_EXPR)
684 {
685 if (!(i % 2))
686 {
687 mz(lc); sprintf(z[lc++],"float %s_y%i;",lname,(i/2));
688 mz(lc); sprintf(z[lc++],"float %s_x%i;",lname,(i/2)+1);
689 }
690 i++;
691 }
692 tptr = tptr->next;
693 }
694 printwavesymblock2(lc, wname);
695 break;
696 }
697 break;
698 case 'w':
699 if (!(strcmp(ident->val,"window")))
700 {
701 z[lc++]="float %2$s_c1;";
702 z[lc++]="float %2$s_c2;";
703 z[lc++]="double %2$s_d1;";
704 z[lc++]="double %2$s_d2;";
705 z[lc++]="double %2$s_d3;";
706 i = 1;
707 while (tptr != NULL)
708 {
709 if (tptr->ttype == S_EXPR)
710 {
711 switch (i) {
712 case 1:
713 z[lc++]="int %2$s_type;";
714 break;
715 case 2:
716 z[lc++]="float %2$s_p;";
717 break;
718 default:
719 printf("Error: Too many parameters for window generator.\n");
720 showerrorplace(sptr->defnode->down->linenum,
721 sptr->defnode->down->filename);
722 }
723 i++;
724 }
725 tptr = tptr->next;
726 }
727 if (i == 1)
728 {
729 printf("Error: Type parameter needed for window generator.\n");
730 showerrorplace(sptr->defnode->down->linenum,
731 sptr->defnode->down->filename);
732 }
733 printwavesymblock2(lc, wname);
734 break;
735 }
736 break;
737 default:
738 break;
739 }
740 free(lname);
741 }
742
743 extern void createwavetable(sigsym *, char *, int);
744
745
746 /*********************************************************/
747 /* high-level routine that creates table code */
748 /* */
749 /* modes values: */
750 /* */
751 /* S_SASLFILE: SASL table commands (readscore.c) */
752 /* S_OPCODE : opcode tables (writeop.c) */
753 /* S_INSTR : instr tables (writeorc.c) */
754 /* S_GLOBAL : global tables (writeorc.c) */
755 /* S_FUTURE : tstamp check (writeorc.c) */
756 /* */
757 /*********************************************************/
758
createtable(sigsym * ident,char * prefix,int mode)759 void createtable(sigsym * ident, char * prefix, int mode)
760
761
762 {
763 int lc = 0;
764 sigsym * gptr;
765
766 switch(ident->kind) {
767 case K_NORMAL:
768 if ((ident->defnode->vol == CONSTANT) && (ident->defnode->usesinput))
769 createconstanttable(ident, prefix, mode);
770 else
771 createwavetable(ident, prefix, mode);
772 break;
773 case K_IMPORT:
774 if ((gptr = getvsym(&globalsymtable, ident->val)) == NULL)
775 internalerror("wtparse.c","createtable");
776 if ((ident->tref->assigntot == 0) && (gptr->tref->assigntot == 0))
777 {
778 /* hash-define statements alias it to global wavetable */
779
780 if (startupinstr && (currinstrument == startupinstr))
781 tablestartupcheck(ident, mode, K_IMPORTEXPORT);
782 break;
783 }
784 if (startupinstr && (currinstrument == startupinstr))
785 tablestartupcheck(ident, mode, K_IMPORT);
786 z[lc++]= "i = NT(%1$s).len = EV(gtables)[TBL_GBL_%2$s].len;";
787 z[lc++]= "NT(%1$s).lenf = EV(gtables)[TBL_GBL_%2$s].lenf;";
788 z[lc++]= "NT(%1$s).start = EV(gtables)[TBL_GBL_%2$s].start;";
789 z[lc++]= "NT(%1$s).end = EV(gtables)[TBL_GBL_%2$s].end;";
790 z[lc++]= "NT(%1$s).base = EV(gtables)[TBL_GBL_%2$s].base;";
791 z[lc++]= "NT(%1$s).stamp = EV(gtables)[TBL_GBL_%2$s].stamp;";
792 z[lc++]= "NT(%1$s).sr = EV(gtables)[TBL_GBL_%2$s].sr;";
793 z[lc++]= "NT(%1$s).tend = EV(gtables)[TBL_GBL_%2$s].tend;";
794 z[lc++]= "NT(%1$s).oconst = EV(gtables)[TBL_GBL_%2$s].oconst;";
795 z[lc++]= "NT(%1$s).dint = EV(gtables)[TBL_GBL_%2$s].dint;";
796 z[lc++]= "NT(%1$s).dfrac = EV(gtables)[TBL_GBL_%2$s].dfrac;";
797 z[lc++]= "NT(%1$s).sffl = EV(gtables)[TBL_GBL_%2$s].sffl;";
798 z[lc++]= "NT(%1$s).sfui = EV(gtables)[TBL_GBL_%2$s].sfui;";
799 z[lc++]= "NT(%1$s).dsincr = EV(gtables)[TBL_GBL_%2$s].dsincr;";
800 if ((ident->tref->assigntval == 0) &&
801 (gptr->tref->assigntval == 0))
802 {
803 z[lc++]= "NT(%1$s).t = EV(gtables)[TBL_GBL_%2$s].t;";
804 }
805 else
806 {
807 z[lc++]= "NT(%1$s).t = (float *) malloc((i+1)*sizeof(float));";
808 z[lc++]= "for(;i >= 0;i--)";
809 z[lc++]= " NT(%1$s).t[i] = EV(gtables)[TBL_GBL_%2$s].t[i];";
810 z[lc++]= "NT(%1$s).llmem = 1;";
811 }
812 printwaveblock(lc,ident,prefix);
813 break;
814 case K_IMPORTEXPORT:
815 /* hash-define statements alias it to global wavetable */
816
817 if (startupinstr && (currinstrument == startupinstr))
818 tablestartupcheck(ident, mode, K_IMPORTEXPORT);
819 break;
820 default:
821 break;
822 }
823 }
824
825 /*********************************************************/
826 /* prints warnings and errors for startup tables */
827 /* called in createtable() above, and in writeop.c */
828 /*********************************************************/
829
tablestartupcheck(sigsym * ident,int mode,int kind)830 void tablestartupcheck(sigsym * ident, int mode, int kind)
831
832 {
833 switch(kind) {
834 case K_IMPORT:
835 switch (mode) {
836 case S_INSTR:
837 printf("Error: Importing table \"%s\" in startup instrument\n"
838 " would cause run-time error, as tables do\n"
839 " not exist until after startup's i-cycle.\n\n",
840 ident->val);
841 showerrorplace(ident->defnode->linenum,
842 ident->defnode->filename);
843 break;
844 case S_OPCODE:
845 printf("Warning: Importing table \"%s\" in an opcode called\n"
846 " by the startup instrument may cause a run-time\n"
847 " error, as tables do not exist during startup's i-cycle.\n\n",
848 ident->val);
849 break;
850 }
851 break;
852 case K_IMPORTEXPORT:
853 switch (mode) {
854 case S_INSTR:
855 printf("Warning: %s table \"%s\" in startup instrument\n"
856 " may cause run-time error, as tables do\n"
857 " not exist until after startup's i-cycle.\n\n",
858 ident->kind == K_IMPORT ? "Importing" : "Import/export of",
859 ident->val);
860 break;
861 case S_OPCODE:
862 printf("Warning: %s table \"%s\" in an opcode called\n"
863 " by the startup instrument may cause a run-time\n"
864 " error, as tables do not exist during startup's i-cycle.\n\n",
865 ident->kind == K_IMPORT ? "Importing" : "Import/export of",
866 ident->val);
867 break;
868 }
869 break;
870 }
871 return;
872 }
873
874
875 /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
876 /* */
877 /* Second-level functions to generate table initialization code */
878 /* */
879 /*______________________________________________________________*/
880
881 extern void wavevarinit(sigsym *, char *);
882 extern void tablepreamble(sigsym *, char *, int, int);
883 extern int tablelistlength(tnode *);
884 extern void samplefilecode(sigsym *, char *, int *);
885 extern void randomconstcode(sigsym *, char *, tnode *, int *);
886
887 /*********************************************************/
888 /* adds code that creates a table */
889 /* */
890 /* TABLE IDENT LP IDENT COM exprstrlist RP */
891 /*********************************************************/
892
createwavetable(sigsym * ident,char * prefix,int mode)893 void createwavetable(sigsym * ident, char * prefix, int mode)
894
895 {
896
897 tnode * genptr = ident->defnode->down->next->next->next;
898 tnode * aptr = ident->defnode->down->next->next->next->next->next->down;
899 int i,j,k;
900 int lc=0;
901 char * lname = makewstring(ident->val);
902
903 wavevarinit(ident,prefix);
904
905 switch (genptr->val[0]) {
906 case 'b':
907 if (!(strcmp(genptr->val,"buzz")))
908 {
909 tablepreamble(ident,prefix,mode,GENBUZZ);
910
911 z[lc++] = "if ((%2$s_rolloff == 1.0F)||(%2$s_rolloff == 0.0F)||";
912 z[lc++] = " (%2$s_rolloff == -1.0F))";
913 z[lc++] = " {";
914 z[lc++] = " %2$s_scale = 1.0F;";
915 z[lc++] = " if ((%2$s_rolloff == 1.0F)||(%2$s_rolloff == -1.0F))";
916 z[lc++] = " %2$s_scale = 1.0F/(1 + %2$s_nharm);";
917 z[lc++] = " }";
918 z[lc++] = "else";
919 z[lc++] = " %2$s_scale = (1.0F-(float)fabs(%2$s_rolloff))/";
920 z[lc++] =" (1-(float)fabs((float)pow(%2$s_rolloff,%2$s_nharm+1)));";
921 z[lc++] = "%2$s_base = 6.283185F/%2$s_size;";
922
923 z[lc++] = "while (i >= 0)";
924 z[lc++] = " {";
925 z[lc++] = " NT(%1$s).t[i] = 0.0F;";
926
927 z[lc++] = " %2$s_index = i*%2$s_base;";
928 z[lc++] = " %2$s_acc = 1.0F;";
929 z[lc++] = " j = %2$s_lowharm + 1;";
930 z[lc++] = " while (j <= (%2$s_lowharm + %2$s_nharm))";
931 z[lc++] = " {";
932 z[lc++] = " NT(%1$s).t[i] += %2$s_acc*(float)cos(%2$s_index*j);";
933 z[lc++] = " %2$s_acc *= %2$s_rolloff;";
934 z[lc++] = " j++;";
935 z[lc++] = " }";
936 z[lc++] = " NT(%1$s).t[i] *= %2$s_scale;";
937 z[lc++] = " i--;";
938 z[lc++] = " }";
939
940 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
941 break;
942 }
943 break;
944 case 'c':
945 if (!(strcmp(genptr->val,"concat")))
946 {
947 tablepreamble(ident, prefix, mode, GENCONCAT);
948
949 z[lc++] = "while (i >= 0)";
950 z[lc++] = " NT(%1$s).t[i--] = 0.0F;";
951 z[lc++] = "i = 0;";
952 j = 1;
953 i = tablelistlength(aptr);
954 while (j <= i)
955 {
956 z[lc++] = "j = 0;";
957 mz(lc); sprintf(z[lc++],
958 "while ((j < AP%i.len) && (i+j < %s_size))",
959 j,lname);
960 z[lc++] = " {";
961 mz(lc); sprintf(z[lc++],
962 " NT(%s_%s).t[i+j] = AP%i.t[j];",
963 prefix,ident->val,j);
964 z[lc++] = " j++;";
965 z[lc++] = " }";
966 mz(lc); sprintf(z[lc++],"i += AP%i.len;", j);
967 j++;
968 }
969
970 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
971 break;
972 }
973 if (!(strcmp(genptr->val,"cubicseg")))
974 {
975 tablepreamble(ident,prefix,mode,GENCUBIC);
976 k = j = tablelistlength(aptr)/4;
977
978 z[lc++]= "while (i >= 0)";
979 z[lc++]= "{";
980 z[lc++]= " NT(%1$s).t[i] = 0.0F;";
981
982 mz(lc); sprintf(z[lc++], " %s_xf = i;", lname);
983
984 while (j >= 1)
985 {
986 mz(lc);
987 if (j == k)
988 sprintf(z[lc++],
989 " if ((i >= %s_infl%i) && (i <= %s_infl%i) )",
990 lname,j,lname,j+1);
991 else
992 sprintf(z[lc++],
993 " if ((i >= %s_infl%i) && (i < %s_infl%i) )",
994 lname,j,lname,j+1);
995 mz(lc); sprintf(z[lc++],
996 " NT(%s_%s).t[i] = %s_xf*%s_xf*%s_xf*%s_a%i + "
997 "%s_xf*%s_xf*%s_b%i + %s_xf*%s_c%i + %s_d%i;",
998 prefix,ident->val,
999 lname, lname, lname, lname,j,
1000 lname, lname, lname, j,
1001 lname, lname, j,
1002 lname, j);
1003
1004 j--;
1005 }
1006 z[lc++]= " i--;";
1007 z[lc++]= "}";
1008
1009 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1010 break;
1011 }
1012 break;
1013 case 'd':
1014 if (!(strcmp(genptr->val,"data")))
1015 {
1016 j = tablelistlength(aptr) - 1;
1017 tablepreamble(ident,prefix,mode,GENNUMDATA);
1018
1019 z[lc++]= " while (i >= 0)";
1020 z[lc++]= " switch(i) {";
1021 while (j>=0)
1022 {
1023 mz(lc); sprintf(z[lc++]," case %i:",j);
1024 mz(lc); sprintf(z[lc++]," NT(%s_%s).t[i--] = %s_p%i;",
1025 prefix,ident->val,lname,j+1);
1026 z[lc++]=" break;";
1027 j--;
1028 }
1029 z[lc++]= " default :";
1030 z[lc++]= " NT(%1$s).t[i--] = 0.0F;";
1031 z[lc++]= "}";
1032
1033 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1034 }
1035 break;
1036 case 'e':
1037 if (!(strcmp(genptr->val,"empty")))
1038 {
1039 if ((aptr->next != NULL))
1040 {
1041 printf("Error: Incorrect number of args.\n");
1042 showerrorplace(ident->defnode->down->linenum,
1043 ident->defnode->down->filename);
1044 }
1045 tablepreamble(ident,prefix,mode,GENILLEGAL);
1046
1047 z[lc++]= "while (i >= 0)";
1048 z[lc++]= " NT(%1$s).t[i--] = 0.0F;";
1049
1050 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1051
1052 break;
1053 }
1054 if (!(strcmp(genptr->val,"expseg")))
1055 {
1056 tablepreamble(ident,prefix,mode,GENPAIRS);
1057 j = tablelistlength(aptr)/2;
1058
1059 z[lc++]= "while (i >= 0)";
1060 z[lc++]= "{";
1061 z[lc++]= " NT(%1$s).t[i] = 0.0F;";
1062 while (j >= 2)
1063 {
1064 mz(lc); sprintf(z[lc++],
1065 " if ((i >= %s_x%i) && (i < %s_x%i) && (%s_x%i != %s_x%i))",
1066 lname,j-1,lname,j,lname,j-1,lname,j);
1067 mz(lc); sprintf(z[lc++],
1068 " NT(%s_%s).t[i] = %s_y%i*(float)pow((double)%s_d%i,",
1069 prefix,ident->val,lname,j-1,lname,j-1);
1070
1071 mz(lc); sprintf(z[lc++],
1072 " (double) %s_e%i*(i - %s_x%i));",
1073 lname,j-1,lname,j-1);
1074
1075 j--;
1076 }
1077 z[lc++]= " i--;";
1078 z[lc++]= "}";
1079
1080 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1081 break;
1082 }
1083 break;
1084 case 'h':
1085 if (!(strcmp(genptr->val,"harm")))
1086 {
1087 tablepreamble(ident,prefix,mode,GENILLEGAL);
1088
1089 z[lc++] = "%2$s_base = 6.283185F/%2$s_size;";
1090 j = tablelistlength(aptr);
1091
1092 z[lc++] = "while (i >= 0)";
1093 z[lc++] = " {";
1094 z[lc++] = " NT(%1$s).t[i] = 0.0F;";
1095 z[lc++] = " %2$s_index = i*%2$s_base;";
1096 while (j>=1)
1097 {
1098 z[lc++] = " NT(%1$s).t[i] += ";
1099 mz(lc); sprintf(z[lc++]," %s_f%i*(float)sin(%i.0F*%s_index);",
1100 lname,j,j,lname);
1101 j--;
1102 }
1103 z[lc++] = " i--;";
1104 z[lc++] = " }";
1105
1106 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1107 break;
1108 }
1109 if (!(strcmp(genptr->val,"harm_phase")))
1110 {
1111 j = tablelistlength(aptr);
1112 if ( (j % 2) == 1)
1113 genex(&lc, ident->defnode->down,
1114 "Odd number of parameters (not including size)");
1115 else
1116 {
1117 tablepreamble(ident,prefix,mode,GENILLEGAL);
1118
1119 z[lc++] = "%2$s_base = 6.283185F/%2$s_size;";
1120 z[lc++] = "while (i >= 0)";
1121 z[lc++] = " {";
1122 z[lc++] = " NT(%1$s).t[i] = 0.0F;";
1123 z[lc++] = " %2$s_index = i*%2$s_base;";
1124 while (j>=2)
1125 {
1126 z[lc++] = " NT(%1$s).t[i] += ";
1127
1128 mz(lc); sprintf(z[lc++],
1129 " %s_f%i*(float)sin((%i.0F*%s_index+ %s_ph%i));",
1130 lname,j/2,j/2,lname,lname,j/2);
1131
1132 j= j - 2;
1133 }
1134 z[lc++] = " i--;";
1135 z[lc++] = " }";
1136 }
1137
1138 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1139 break;
1140 }
1141 break;
1142 case 'l':
1143 if (!(strcmp(genptr->val,"lineseg")))
1144 {
1145
1146 tablepreamble(ident,prefix,mode,GENPAIRS);
1147 j = tablelistlength(aptr)/2;
1148
1149 z[lc++]= "while (i >= 0)";
1150 z[lc++]= "{";
1151 z[lc++]= " NT(%1$s).t[i] = 0.0F;";
1152 while (j >= 2)
1153 {
1154 mz(lc); sprintf(z[lc++],
1155 " if ((i >= %s_x%i) && (i < %s_x%i) && (%s_x%i != %s_x%i))",
1156 lname,j-1,lname,j,lname,j-1,lname,j);
1157 mz(lc); sprintf(z[lc++],
1158 " NT(%s_%s).t[i] = %s_y%i + %s_d%i*(i - %s_x%i);",
1159 prefix,ident->val,lname,j-1,lname,j-1,lname,j-1);
1160
1161 j--;
1162 }
1163 z[lc++]= " i--;";
1164 z[lc++]= "}";
1165
1166 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1167 break;
1168 }
1169 break;
1170 case 'p':
1171 if (!(strcmp(genptr->val,"periodic")))
1172 {
1173 j = tablelistlength(aptr);
1174 if ( (j % 3) != 0)
1175 genex(&lc, ident->defnode->down,
1176 "Number of parameters not divisible by 3");
1177 else
1178 {
1179 tablepreamble(ident,prefix,mode,GENILLEGAL);
1180
1181 z[lc++] = "%2$s_base = 6.283185F/%2$s_size;";
1182 z[lc++] = "while (i >= 0)";
1183 z[lc++] = " {";
1184 z[lc++] = " NT(%1$s).t[i] = 0.0F;";
1185 z[lc++] = " %2$s_index = i*%2$s_base;";
1186
1187 while (j>=3)
1188 {
1189 z[lc++] = " NT(%1$s).t[i] += ";
1190
1191 mz(lc); sprintf(z[lc++],
1192 " %s_f%i*(float)sin(%s_p%i*%s_index+ %s_ph%i);",
1193 lname,j/3,lname,j/3, lname,lname,j/3);
1194
1195 j= j - 3;
1196 }
1197 z[lc++] = " i--;";
1198 z[lc++] = " }";
1199 }
1200
1201 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1202 break;
1203 }
1204 if (!(strcmp(genptr->val,"polynomial")))
1205 {
1206 tablepreamble(ident,prefix,mode,GENILLEGAL);
1207
1208 i = tablelistlength(aptr) -3;
1209 j = 0;
1210 z[lc++] = "%2$s_scale = (1.0F/%2$s_size)*(%2$s_xmax-%2$s_xmin);";
1211 z[lc++] = "while (i >= 0)";
1212 z[lc++] = " {";
1213 z[lc++] = " NT(%1$s).t[i] = 0.0F;";
1214 z[lc++] = " %2$s_index = %2$s_xmin + %2$s_scale*(%2$s_size - i);";
1215 z[lc++] = " %2$s_acc = 1.0F;";
1216 z[lc++] = " NT(%1$s).t[i] = %2$s_a0;";
1217 while (j < i)
1218 {
1219 z[lc++] = " %2$s_acc *= %2$s_index;";
1220 mz(lc); sprintf(z[lc++]," NT(%s_%s).t[i] += %s_a%i*%s_acc;",
1221 prefix,ident->val,lname,j+1,lname);
1222 j++;
1223 }
1224 z[lc++] = " i--;";
1225 z[lc++] = " }";
1226
1227 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1228 break;
1229 }
1230 break;
1231 case 'r':
1232 if (!(strcmp(genptr->val,"random")))
1233 {
1234 j = tablelistlength(aptr);
1235 tablepreamble(ident,prefix,mode,GENILLEGAL);
1236
1237 if (aptr->next->next->vol == CONSTANT)
1238 {
1239 randomconstcode(ident, prefix, aptr, &lc);
1240 break;
1241 }
1242
1243 /* general-purpose code: only used if dist is a variable */
1244
1245 z[lc++] = "switch(%2$s_dist) {";
1246 z[lc++] = " case 1:";
1247 if (j==3)
1248 z[lc++] = " %2$s_c1 = %2$s_p2 - %2$s_p1;";
1249 else
1250 genex(&lc, ident->defnode->down, "Wrong number of parameters (dist 1)");
1251
1252 z[lc++] = " break;";
1253 z[lc++] = " case 2:";
1254 if (j==3)
1255 {
1256 z[lc++] = " %2$s_c1 = %2$s_p2 - %2$s_p1;";
1257 z[lc++] = "if (%2$s_p2 == %2$s_p1)";
1258 genex(&lc, ident->defnode->down, "p1 == p2 (dist 2)");
1259 }
1260 else
1261 genex(&lc, ident->defnode->down, "Wrong number of parameters (dist 2)");
1262
1263 z[lc++] = " break;";
1264 z[lc++] = " case 3:";
1265 z[lc++] = " break;";
1266 z[lc++] = " case 4:";
1267 if (j==3)
1268 {
1269 z[lc++] = " if (%2$s_p2 <= 0.0F)";
1270 genex(&lc, ident->defnode->down, "p2 <= 0 (dist 4)");
1271 z[lc++] = " %2$s_c1 = (float)sqrt(2*%2$s_p2);";
1272 }
1273 else
1274 genex(&lc, ident->defnode->down, "Wrong number of parameters (dist 4)");
1275
1276 z[lc++] = " break;";
1277 z[lc++] = " case 5:";
1278 z[lc++] = " break;";
1279 z[lc++] = " default:";
1280 genex(&lc, ident->defnode->down, "Illegal distribution (not 1,2,3,4,5)");
1281 z[lc++] = "}";
1282
1283 z[lc++] = "j = 0; i = 0;";
1284 z[lc++] = "while (i < %2$s_size)";
1285 z[lc++] = " {";
1286 z[lc++] = " switch(%2$s_dist) {";
1287 z[lc++] = " case 1:";
1288 z[lc++] = " NT(%1$s).t[i] = %2$s_c1*RMULT*((float)rand()) + %2$s_p1;";
1289 z[lc++] = " break;";
1290 z[lc++] = " case 2:";
1291 z[lc++] = " %2$s_x = RMULT*((float)rand());";
1292 z[lc++] = " %2$s_y = RMULT*((float)rand());";
1293 z[lc++] = " if (%2$s_x > %2$s_y)";
1294 z[lc++] = " NT(%1$s).t[i] = %2$s_c1*%2$s_x + %2$s_p1;";
1295 z[lc++] = " else";
1296 z[lc++] = " NT(%1$s).t[i] = %2$s_c1*%2$s_y + %2$s_p1;";
1297 z[lc++] = " break;";
1298 z[lc++] = " case 3:";
1299 z[lc++] = " NT(%1$s).t[i] = -%2$s_p1*(float)log(RMULT*((float)rand())+1e-45F);";
1300 z[lc++] = " break;";
1301 z[lc++] = " case 4:";
1302 z[lc++] = " NT(%1$s).t[i] = %2$s_p1+%2$s_c1*";
1303 z[lc++] = " (float)sqrt(-2.0F*(float)log(RMULT*((float)rand())+1e-45F))";
1304 z[lc++] = " *(float)cos(6.283185F*RMULT*((float)rand()));";
1305 z[lc++] = " break;";
1306 z[lc++] = " case 5:";
1307 z[lc++] = " NT(%1$s).t[i] = 0;";
1308 z[lc++] = " if (j == 0)";
1309 z[lc++] = " {";
1310 z[lc++] = " j = ROUND(-%2$s_p1*(float)log(RMULT*((float)rand())+1e-45F))+1;";
1311 z[lc++] = " if (i != 0)";
1312 z[lc++] = " NT(%1$s).t[i] = 1.0F;";
1313 z[lc++] = " }";
1314 z[lc++] = " j--;";
1315 z[lc++] = " break;";
1316 z[lc++] = " }";
1317 z[lc++] = " i++;";
1318 z[lc++] = " }";
1319 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1320 }
1321 break;
1322 case 's':
1323 if (!(strcmp(genptr->val,"sample")))
1324 {
1325 samplefilecode(ident, prefix, &lc);
1326 break;
1327 }
1328 if (!(strcmp(genptr->val,"spline")))
1329 {
1330 tablepreamble(ident,prefix,mode,GENSPLINE);
1331 k = j = ((tablelistlength(aptr)+1)/3)-1;
1332
1333 z[lc++]= "while (i >= 0)";
1334 z[lc++]= "{";
1335 z[lc++]= " NT(%1$s).t[i] = 0.0F;";
1336
1337 mz(lc); sprintf(z[lc++], " %s_xf = i;", lname);
1338
1339 while (j >= 1)
1340 {
1341 mz(lc);
1342 if (j == k)
1343 sprintf(z[lc++],
1344 " if ((i >= %s_x%i) && (i <= %s_x%i) && (%s_x%i != %s_x%i))",
1345 lname,j,lname,j+1,lname,j,lname,j+1);
1346 else
1347 sprintf(z[lc++],
1348 " if ((i >= %s_x%i) && (i < %s_x%i) && (%s_x%i != %s_x%i))",
1349 lname,j,lname,j+1,lname,j,lname,j+1);
1350 mz(lc); sprintf(z[lc++],
1351 " NT(%s_%s).t[i] = %s_xf*%s_xf*%s_xf*%s_a%i + "
1352 "%s_xf*%s_xf*%s_b%i + %s_xf*%s_c%i + %s_d%i;",
1353
1354 prefix,ident->val, lname, lname, lname, lname, j,
1355 lname, lname, lname,j,
1356 lname, lname,j,
1357 lname,j);
1358
1359 j--;
1360 }
1361 z[lc++]= " i--;";
1362 z[lc++]= "}";
1363 z[lc++]= " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1364 break;
1365 }
1366 if (!(strcmp(genptr->val,"step")))
1367 {
1368
1369 tablepreamble(ident,prefix,mode,GENSTEP);
1370 j = (tablelistlength(aptr)/2)+1;
1371
1372 z[lc++]= "while (i >= 0)";
1373 z[lc++]= "{";
1374 z[lc++]= " NT(%1$s).t[i] = 0.0F;";
1375 while (j >= 2)
1376 {
1377 mz(lc); sprintf(z[lc++],
1378 " if ((i >= %s_x%i) && (i < %s_x%i))",
1379 lname,j-1,lname,j);
1380 mz(lc); sprintf(z[lc++],
1381 " NT(%s_%s).t[i] = %s_y%i;", prefix,ident->val,lname,j-1);
1382
1383 j--;
1384 }
1385 z[lc++]= " i--;";
1386 z[lc++]= "}";
1387
1388 z[lc++]= " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1389 break;
1390 }
1391 break;
1392 case 'w':
1393 if (!(strcmp(genptr->val,"window")))
1394 {
1395 j = tablelistlength(aptr);
1396 tablepreamble(ident,prefix,mode,GENILLEGAL);
1397
1398
1399 z[lc++] = "switch(%2$s_type) {";
1400 z[lc++] = " case 1:";
1401 z[lc++] = " case 2:";
1402 z[lc++] = " %2$s_c1 = 6.283185F/(%2$s_size-1.0F);";
1403 z[lc++] = " break;";
1404 z[lc++] = " case 3:";
1405 z[lc++] = " %2$s_c1 = 2.0F/(%2$s_size-1.0F);";
1406 z[lc++] = " %2$s_c2 = 1.0F/%2$s_c1;";
1407 z[lc++] = " break;";
1408 z[lc++] = " case 4:";
1409 z[lc++] = " %2$s_c1 = - 18.0F/(%2$s_size*%2$s_size);";
1410 z[lc++] = " %2$s_c2 = - 0.5F*%2$s_size;";
1411 z[lc++] = " break;";
1412 z[lc++] = " case 5:";
1413 if (j==2)
1414 {
1415 z[lc++] = " %2$s_d1 = (%2$s_size-1.0)/2.0;";
1416 z[lc++] = " %2$s_d2 = %2$s_d1*%2$s_d1;";
1417 z[lc++] = " %2$s_d3 = 1.0/modbessel(%2$s_p*%2$s_d1);";
1418 }
1419 else
1420 genex(&lc, ident->defnode->down, "Parameter p needed (type 5)");
1421 z[lc++] = " break;";
1422 z[lc++] = " case 6:";
1423 z[lc++] = " break;";
1424 z[lc++] = " default:";
1425 genex(&lc, ident->defnode->down, "Illegal window type (not 1,2,3,4,5,6)");
1426
1427 z[lc++] = "}";
1428
1429
1430 z[lc++] = "while (i >= 0)";
1431 z[lc++] = " {";
1432 z[lc++] = " switch(%2$s_type) {";
1433 z[lc++] = " case 1:";
1434 z[lc++] = " NT(%1$s).t[i] = 0.54F - 0.46F*(float)cos(%2$s_c1*i);";
1435 z[lc++] = " break;";
1436 z[lc++] = " case 2:";
1437 z[lc++] = " NT(%1$s).t[i] = 0.5F*(1.0F - (float)cos(%2$s_c1*i));";
1438 z[lc++] = " break;";
1439 z[lc++] = " case 3:";
1440 z[lc++] = " NT(%1$s).t[i] = 1.0F - %2$s_c1*(float)fabs(i - %2$s_c2);";
1441 z[lc++] = " break;";
1442 z[lc++] = " case 4:";
1443 z[lc++] = " NT(%1$s).t[i] = ";
1444 z[lc++] = " (float)exp(%2$s_c1*(%2$s_c2+i)*(%2$s_c2+i));";
1445 z[lc++] = " break;";
1446 z[lc++] = " case 5:";
1447 if (j==2)
1448 {
1449 z[lc++] = " NT(%1$s).t[i] = (float)(%2$s_d3*modbessel(%2$s_p*";
1450 z[lc++] = " sqrt(%2$s_d2 - (i-%2$s_d1)*(i-%2$s_d1))));";
1451 }
1452 z[lc++] = " break;";
1453 z[lc++] = " case 6:";
1454 z[lc++] = " NT(%1$s).t[i] = 1.0F;";
1455 z[lc++] = " break;";
1456 z[lc++] = " }";
1457 z[lc++] = " i--;";
1458 z[lc++] = " }";
1459
1460 z[lc++]= " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
1461 }
1462 break;
1463 default:
1464 break;
1465 }
1466 printwavesymblock(lc,ident,prefix);
1467 free(lname);
1468 }
1469
1470
1471 /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
1472 /* */
1473 /* Lower-level functions wavevarinit() and tablepreamble() */
1474 /* do large code-generation subtasks for createwavetable(). */
1475 /* */
1476 /*______________________________________________________________*/
1477
1478 extern void wavevarinitcheck(tnode *);
1479
1480 /*********************************************************/
1481 /* initializes variables for generator execution */
1482 /*********************************************************/
1483
wavevarinit(sigsym * sptr,char * prefix)1484 void wavevarinit(sigsym * sptr, char * prefix)
1485
1486
1487 {
1488 tnode * wname = sptr->defnode->down->next;
1489 tnode * ident = sptr->defnode->down->next->next->next;
1490 tnode * tptr = sptr->defnode->down->next->next->next->next->next->down;
1491 int i, j, depth, currblocksafe;
1492 int lc = 0;
1493 int tabletype; /* for concat */
1494 char tablename[STRSIZE];
1495 char * idxstr;
1496 char * lname = makewstring(wname->val);
1497
1498 currblocksafe = currblockrate;
1499 currblockrate = IRATETYPE;
1500
1501 if (tptr == NULL)
1502 {
1503 printf("Error: Generator needs size parameter.\n");
1504 showerrorplace(wname->linenum, wname->filename);
1505 }
1506 wavevarinitcheck(tptr);
1507
1508 fprintf(outfile," %s_rounding = ", lname);
1509 blocktree(tptr->down, PRINTTOKENS);
1510 fprintf(outfile,";\n");
1511
1512 fprintf(outfile," %s_size = ROUND(%s_rounding);\n",
1513 lname, lname);
1514
1515 tptr = tptr->next;
1516 if (tptr != NULL)
1517 tptr = tptr->next;
1518
1519 switch (ident->val[0]) {
1520 case 'b':
1521 if (!(strcmp(ident->val,"buzz")))
1522 {
1523 i = 1;
1524 while (tptr != NULL)
1525 {
1526 if (tptr->ttype == S_EXPR)
1527 {
1528 wavevarinitcheck(tptr);
1529 switch (i) {
1530 case 1:
1531 fprintf(outfile," %s_rounding = ", lname);
1532 blocktree(tptr->down, PRINTTOKENS);
1533 fprintf(outfile,";\n");
1534 fprintf(outfile," %s_nharm = ROUND(%s_rounding);\n",
1535 lname, lname);
1536 break;
1537 case 2:
1538 fprintf(outfile," %s_rounding = ", lname);
1539 blocktree(tptr->down, PRINTTOKENS);
1540 fprintf(outfile,";\n");
1541 fprintf(outfile," %s_lowharm = ROUND(%s_rounding);\n",
1542 lname, lname);
1543 break;
1544 case 3:
1545 fprintf(outfile," %s_rolloff = ",lname);
1546 blocktree(tptr->down, PRINTTOKENS);
1547 fprintf(outfile,";\n");
1548 break;
1549 }
1550 i++;
1551 }
1552 tptr = tptr->next;
1553 }
1554 break;
1555 }
1556 break;
1557 case 'c':
1558 if (!(strcmp(ident->val,"concat")))
1559 {
1560 i = 1;
1561 while (tptr != NULL)
1562 {
1563 if (tptr->ttype == S_EXPR)
1564 {
1565 if (!(tptr->vartype == TABLETYPE))
1566 {
1567 printf("Error: Concat ft args must be tables.\n");
1568 showerrorplace(wname->linenum, wname->filename);
1569 }
1570 currarrayindex = 0;
1571 currscalarflag = 1;
1572 sprintf(tablename,"%s_ft%i",lname,i);
1573 if (tptr->down->next == NULL)
1574 {
1575 /* a table */
1576
1577 fprintf(outfile," %s = ", tablename);
1578 tabletype = maketableindex(tptr->down, curropcodestack,
1579 &idxstr, &depth);
1580 fprintf(outfile,"%s;\n",idxstr);
1581 printtabledefine(i++, tablename, tabletype, depth);
1582 }
1583 else
1584 {
1585
1586 /* a tablemap */
1587
1588 printtmapcase(tptr->down,
1589 tptr->down->next->next, tablename);
1590 printtabledefine(i++, tablename, S_TABLEMAP, -1);
1591 }
1592 }
1593 tptr = tptr->next;
1594 }
1595 break;
1596 }
1597 if (!(strcmp(ident->val,"cubicseg")))
1598 {
1599 i = 1; j = 0;
1600 while (tptr != NULL)
1601 {
1602 if (tptr->ttype == S_EXPR)
1603 {
1604 wavevarinitcheck(tptr);
1605 switch (j) {
1606 case 0:
1607 fprintf(outfile," %s_rounding = ", lname);
1608 blocktree(tptr->down, PRINTTOKENS);
1609 fprintf(outfile,";\n");
1610 fprintf(outfile," %s_infl%i = ROUND(%s_rounding);\n",
1611 lname,i,lname);
1612 break;
1613 case 1:
1614 fprintf(outfile," %s_y%i = ",lname, 2*i-1);
1615 blocktree(tptr->down, PRINTTOKENS);
1616 fprintf(outfile,";\n");
1617 break;
1618 case 2:
1619 fprintf(outfile," %s_rounding = ", lname);
1620 blocktree(tptr->down, PRINTTOKENS);
1621 fprintf(outfile,";\n");
1622 fprintf(outfile," %s_x%i = ROUND(%s_rounding);\n",
1623 lname,i,lname);
1624 break;
1625 case 3:
1626 fprintf(outfile," %s_y%i = ",lname, 2*i);
1627 blocktree(tptr->down, PRINTTOKENS);
1628 fprintf(outfile,";\n");
1629 break;
1630 }
1631 j++;
1632 if (j == 4)
1633 {
1634 j = 0; i++;
1635 }
1636 }
1637 tptr = tptr->next;
1638 }
1639 z[lc++] = "if (%2$s_infl1 != 0.0F)";
1640 genex(&lc, wname, "First inflection point != 0");
1641 i--;
1642 if ((j != 2)|| (i<2))
1643 genex(&lc, wname, "Not enough x values");
1644 else
1645 {
1646 j = 1;
1647 while (j <= i)
1648 {
1649 z[lc++] = "";
1650 mz(lc); sprintf(z[lc++],
1651 "if (%s_x%i <= %s_infl%i)",
1652 lname,j,lname,j);
1653 genex(&lc, wname, "Infl not strictly between surrounding xvals");
1654 mz(lc); sprintf(z[lc++],
1655 "if (%s_infl%i <= %s_x%i)",
1656 lname,j+1,lname,j);
1657 genex(&lc, wname, "Infl not strictly between surrounding xvals");
1658
1659 mz(lc); sprintf(z[lc++],
1660 "%s_Q = %s_infl%i*%s_infl%i*%s_infl%i;",
1661 lname,lname,j,lname,j,lname,j);
1662 mz(lc); sprintf(z[lc++],
1663 "%s_Q += - %s_x%i*%s_x%i*%s_x%i;",
1664 lname,lname,j,lname,j,lname,j);
1665 mz(lc); sprintf(z[lc++],
1666 "%s_Q += - 3.0F*%s_x%i*%s_x%i*(%s_infl%i-%s_x%i);",
1667 lname,lname,j,lname,
1668 j,lname,j,lname,j);
1669 mz(lc); sprintf(z[lc++],
1670 "if (%s_Q == 0.0F)",
1671 lname);
1672 genex(&lc, wname, "No cubic solution for these parameters");
1673
1674 mz(lc); sprintf(z[lc++],
1675 "%s_R = %s_infl%i*%s_infl%i;",
1676 lname,lname,j,lname,j);
1677 mz(lc); sprintf(z[lc++],
1678 "%s_R += - %s_x%i*%s_x%i;",
1679 lname,lname,j,lname,j);
1680 mz(lc); sprintf(z[lc++],
1681 "%s_R += - 2.0F*%s_x%i*(%s_infl%i-%s_x%i);",
1682 lname,lname,j,lname,j
1683 ,lname,j);
1684 mz(lc); sprintf(z[lc++],
1685 "if (%s_R == 0.0F)",
1686 lname);
1687 genex(&lc, wname, "No cubic solution for these parameters");
1688
1689 mz(lc); sprintf(z[lc++],
1690 "%s_S = %s_x%i*%s_x%i*%s_x%i;",
1691 lname,lname,j,lname,j
1692 ,lname,j);
1693 mz(lc); sprintf(z[lc++],
1694 "%s_S += - %s_infl%i*%s_infl%i*%s_infl%i;",
1695 lname,lname,j+1,lname,j+1
1696 ,lname,j+1);
1697 mz(lc); sprintf(z[lc++],
1698 "%s_S += - 3.0F*%s_x%i*%s_x%i*(%s_x%i-%s_infl%i);"
1699 ,lname,lname,j,lname,j
1700 ,lname,j,lname,j+1);
1701 mz(lc); sprintf(z[lc++],
1702 "if (%s_S == 0.0F)",
1703 lname);
1704 genex(&lc, wname, "No cubic solution for these parameters");
1705
1706 mz(lc); sprintf(z[lc++],
1707 "%s_T = %s_x%i*%s_x%i;",
1708 lname,lname,j,lname,j);
1709 mz(lc); sprintf(z[lc++],
1710 "%s_T += - %s_infl%i*%s_infl%i;",
1711 lname,lname,j+1,lname,j+1);
1712 mz(lc); sprintf(z[lc++],
1713 "%s_T += - 2.0F*%s_x%i*(%s_x%i-%s_infl%i);"
1714 ,lname,lname,j,lname,j
1715 ,lname,j+1);
1716 mz(lc); sprintf(z[lc++],
1717 "if (%s_T == 0.0F)",
1718 lname);
1719 genex(&lc, wname, "No cubic solution for these parameters");
1720
1721 mz(lc); sprintf(z[lc++],
1722 "if ((%s_Q/%s_R) == (%s_S/%s_T))",
1723 lname,lname,lname,lname);
1724 genex(&lc, wname, "No cubic solution for these parameters");
1725
1726 mz(lc); sprintf(z[lc++],
1727 "%s_a%i = 1.0F/((%s_Q/%s_R) - (%s_S/%s_T));",
1728 lname,j,lname,lname,
1729 lname,lname);
1730 mz(lc); sprintf(z[lc++],
1731 "%s_a%i *= (%s_y%i-%s_y%i)/%s_R - (%s_y%i-%s_y%i)/%s_T;",
1732 lname,j,
1733 lname,2*j-1,
1734 lname,2*j,
1735 lname,
1736 lname,2*j,
1737 lname,2*j+1,
1738 lname);
1739
1740 mz(lc); sprintf(z[lc++],
1741 "%s_b%i = 1.0F/((%s_R/%s_Q) - (%s_T/%s_S));",
1742 lname,j,lname,lname,
1743 lname,lname);
1744 mz(lc); sprintf(z[lc++],
1745 "%s_b%i *= (%s_y%i-%s_y%i)/%s_Q - (%s_y%i-%s_y%i)/%s_S;",
1746 lname,j,
1747 lname,2*j-1,
1748 lname,2*j,
1749 lname,
1750 lname,2*j,
1751 lname,2*j+1,
1752 lname);
1753
1754 mz(lc); sprintf(z[lc++],
1755 "%s_c%i = - 3.0F*%s_a%i*%s_x%i*%s_x%i - 2.0F*%s_b%i*%s_x%i;",
1756 lname,j, lname,j,
1757 lname,j, lname,j,
1758 lname,j, lname,j);
1759 mz(lc); sprintf(z[lc++],
1760 "%s_d%i = %s_y%i - %s_a%i*%s_x%i*%s_x%i*%s_x%i;",
1761 lname,j, lname,2*j,
1762 lname,j, lname,j,
1763 lname,j, lname,j);
1764
1765 mz(lc); sprintf(z[lc++],
1766 "%s_d%i += - %s_b%i*%s_x%i*%s_x%i - %s_c%i*%s_x%i;"
1767 ,lname,j,lname,j
1768 ,lname,j,lname,j
1769 ,lname,j,lname,j);
1770
1771 j++;
1772 }
1773 z[lc++]="";
1774
1775 }
1776 printwavesymblock2(lc,wname);
1777 break;
1778 }
1779 break;
1780 case 'd':
1781 if (!(strcmp(ident->val,"data")))
1782 {
1783 i = 1;
1784 while (tptr != NULL)
1785 {
1786 if (tptr->ttype == S_EXPR)
1787 {
1788 wavevarinitcheck(tptr);
1789 fprintf(outfile," %s_p%i = ",lname,i);
1790 blocktree(tptr->down, PRINTTOKENS);
1791 fprintf(outfile,";\n");
1792 i++;
1793 }
1794 tptr = tptr->next;
1795 }
1796 break;
1797 }
1798 break;
1799 case 'e':
1800 if (!(strcmp(ident->val,"empty")))
1801 {
1802 break;
1803 }
1804 if (!(strcmp(ident->val,"expseg")))
1805 {
1806 i = 1;
1807 while (tptr != NULL)
1808 {
1809 if (tptr->ttype == S_EXPR)
1810 {
1811 wavevarinitcheck(tptr);
1812 if ((i % 2) == 1)
1813 {
1814 fprintf(outfile," %s_rounding = ", lname);
1815 blocktree(tptr->down, PRINTTOKENS);
1816 fprintf(outfile,";\n");
1817 fprintf(outfile," %s_x%i = ROUND(%s_rounding);\n",
1818 lname, (i/2)+1, lname);
1819 }
1820 else
1821 {
1822 fprintf(outfile," %s_y%i = ",lname,(i/2));
1823 blocktree(tptr->down, PRINTTOKENS);
1824 fprintf(outfile,";\n");
1825 }
1826 i++;
1827 }
1828 tptr = tptr->next;
1829 }
1830 i--;
1831 if (i % 2 == 1)
1832 genex(&lc, wname, "Odd number of parameters (not including size)");
1833 else
1834 {
1835 i = i/2;
1836 while (i >= 2)
1837 {
1838 mz(lc); sprintf(z[lc++],"if (%s_x%i > %s_x%i)",
1839 lname,i-1,lname,i);
1840 genex(&lc, wname, "xvals not a non-decreasing sequence");
1841 mz(lc); sprintf(z[lc++],"if (%s_y%i == 0.0F)",
1842 lname,i);
1843 genex(&lc, wname, "yval == 0.0F");
1844 mz(lc); sprintf(z[lc++],"if ((%s_y%i>0.0F) != (%s_y%i>0.0F))",
1845 lname,i-1,lname,i);
1846 genex(&lc, wname, "yvals not all the same sign");
1847 mz(lc); sprintf(z[lc++],"%s_d%i = %s_y%i/%s_y%i;",
1848 lname,i-1,lname,i,lname,i-1);
1849 mz(lc); sprintf(z[lc++],"if (%s_x%i != %s_x%i)",
1850 lname,i-1,lname,i);
1851 mz(lc); sprintf(z[lc++],"%s_e%i= 1.0F/(%s_x%i-%s_x%i);",
1852 lname,i-1,
1853 lname,i,
1854 lname,i-1);
1855 i--;
1856 }
1857 z[lc++]="if (%2$s_x1 != 0.0F)";
1858 genex(&lc, wname, "x1 is not equal to zero");
1859 z[lc++]="if (%2$s_y1 == 0.0F)";
1860 genex(&lc, wname, "y1 is equal to zero");
1861 }
1862 printwavesymblock2(lc,wname);
1863 break;
1864 }
1865 break;
1866 case 'h':
1867 if (!(strcmp(ident->val,"harm")))
1868 {
1869 i = 1;
1870 while (tptr != NULL)
1871 {
1872 if (tptr->ttype == S_EXPR)
1873 {
1874 wavevarinitcheck(tptr);
1875 fprintf(outfile," %s_f%i = ",lname,i);
1876 i++;
1877 blocktree(tptr->down, PRINTTOKENS);
1878 fprintf(outfile,";\n");
1879 }
1880 tptr = tptr->next;
1881 }
1882 break;
1883 }
1884 if (!(strcmp(ident->val,"harm_phase")))
1885 {
1886 i = 1;
1887 while (tptr != NULL)
1888 {
1889 if (tptr->ttype == S_EXPR)
1890 {
1891 wavevarinitcheck(tptr);
1892 if ((i % 2) == 1)
1893 fprintf(outfile," %s_f%i = ",lname,(i/2)+1);
1894 else
1895 fprintf(outfile," %s_ph%i = ",lname,(i/2));
1896 blocktree(tptr->down, PRINTTOKENS);
1897 fprintf(outfile,";\n");
1898 i++;
1899 }
1900 tptr = tptr->next;
1901 }
1902 break;
1903 }
1904 break;
1905 case 'l':
1906 if (!(strcmp(ident->val,"lineseg")))
1907 {
1908 i = 1;
1909 while (tptr != NULL)
1910 {
1911 if (tptr->ttype == S_EXPR)
1912 {
1913 wavevarinitcheck(tptr);
1914 if ((i % 2) == 1)
1915 {
1916 fprintf(outfile," %s_rounding = ", lname);
1917 blocktree(tptr->down, PRINTTOKENS);
1918 fprintf(outfile,";\n");
1919 fprintf(outfile," %s_x%i = ROUND(%s_rounding);\n",
1920 lname, (i/2)+1, lname);
1921 }
1922 else
1923 {
1924 fprintf(outfile," %s_y%i = (",lname,(i/2));
1925 blocktree(tptr->down, PRINTTOKENS);
1926 fprintf(outfile,");\n");
1927 }
1928 i++;
1929 }
1930 tptr = tptr->next;
1931 }
1932 i--;
1933 if (i % 2 == 1)
1934 genex(&lc, wname, "Odd number of parameters (not including size)");
1935 else
1936 {
1937 i = i/2;
1938 while (i >= 2)
1939 {
1940 mz(lc); sprintf(z[lc++],
1941 "if (%s_x%i > %s_x%i)",
1942 lname,i-1,lname,i);
1943 genex(&lc, wname, "xvals not a non-decreasing sequence");
1944 mz(lc); sprintf(z[lc++],
1945 "if (%s_x%i != %s_x%i)",
1946 lname,i-1,lname,i);
1947 mz(lc); sprintf(z[lc++],
1948 "%s_d%i=(%s_y%i-%s_y%i)/(%s_x%i-%s_x%i);",
1949 lname,i-1, lname,i,
1950 lname,i-1, lname,i,lname,i-1);
1951 i--;
1952 }
1953 z[lc++]="if (%2$s_x1 != 0.0F)";
1954 genex(&lc, wname, "x1 != 0");
1955 }
1956 printwavesymblock2(lc,wname);
1957 break;
1958 }
1959 break;
1960 case 'p':
1961 if (!(strcmp(ident->val,"periodic")))
1962 {
1963 i = 1;
1964 while (tptr != NULL)
1965 {
1966 if (tptr->ttype == S_EXPR)
1967 {
1968 wavevarinitcheck(tptr);
1969 switch(i % 3) {
1970 case 1:
1971 fprintf(outfile," %s_p%i = ",lname,(i/3)+1);
1972 break;
1973 case 2:
1974 fprintf(outfile," %s_f%i = ",lname,(i/3)+1);
1975 break;
1976 case 0:
1977 fprintf(outfile," %s_ph%i = ",lname,(i/3));
1978 break;
1979 }
1980 blocktree(tptr->down, PRINTTOKENS);
1981 fprintf(outfile,";\n");
1982 i++;
1983 }
1984 tptr = tptr->next;
1985 }
1986 break;
1987 }
1988 if (!(strcmp(ident->val,"polynomial")))
1989 {
1990 i = 1;
1991 while (tptr != NULL)
1992 {
1993 if (tptr->ttype == S_EXPR)
1994 {
1995 switch (i) {
1996 case 1:
1997 fprintf(outfile," %s_xmin = ",lname);
1998 break;
1999 case 2:
2000 fprintf(outfile," %s_xmax = ",lname);
2001 break;
2002 default:
2003 fprintf(outfile," %s_a%i = ",lname,i-3);
2004 break;
2005 }
2006 blocktree(tptr->down, PRINTTOKENS);
2007 fprintf(outfile,";\n");
2008 i++;
2009 }
2010 tptr = tptr->next;
2011 }
2012 if (i<4)
2013 genex(&lc, wname, "Not enough parameters");
2014 z[lc++]="if (%2$s_xmax == %2$s_xmin)";
2015 genex(&lc, wname, "xmin = xmax");
2016 printwavesymblock2(lc,wname);
2017 break;
2018 }
2019 break;
2020 case 'r':
2021 if (!(strcmp(ident->val,"random")))
2022 {
2023 i = 1;
2024 while (tptr != NULL)
2025 {
2026 if (tptr->ttype == S_EXPR)
2027 {
2028 wavevarinitcheck(tptr);
2029 switch (i) {
2030 case 1:
2031 fprintf(outfile," %s_rounding = ", lname);
2032 blocktree(tptr->down, PRINTTOKENS);
2033 fprintf(outfile,";\n");
2034 fprintf(outfile," %s_dist = ROUND(%s_rounding);\n",
2035 lname, lname);
2036 break;
2037 case 2:
2038 fprintf(outfile," %s_p1 = ",lname);
2039 blocktree(tptr->down, PRINTTOKENS);
2040 fprintf(outfile,";\n");
2041 break;
2042 case 3:
2043 fprintf(outfile," %s_p2 = ",lname);
2044 blocktree(tptr->down, PRINTTOKENS);
2045 fprintf(outfile,";\n");
2046 break;
2047 default:
2048 printf("Error: Too many parameters.\n");
2049 showerrorplace(wname->linenum, wname->filename);
2050 }
2051 i++;
2052 }
2053 tptr = tptr->next;
2054 }
2055 break;
2056 }
2057 break;
2058 case 's':
2059 if (!(strcmp(ident->val,"sample")))
2060 {
2061 /* check skip if present, codegen in samplefilecode */
2062
2063 tptr = (tptr->next) ? tptr->next->next : NULL;
2064
2065 if (tptr)
2066 wavevarinitcheck(tptr);
2067
2068 break;
2069 }
2070 if (!(strcmp(ident->val,"spline")))
2071 {
2072 i = 1; j = 1;
2073 while (tptr != NULL)
2074 {
2075 if (tptr->ttype == S_EXPR)
2076 {
2077 wavevarinitcheck(tptr);
2078 switch(i % 3) {
2079 case 0:
2080 fprintf(outfile," %s_k%i = ",lname,(i/3)+1);
2081 blocktree(tptr->down, PRINTTOKENS);
2082 fprintf(outfile,";\n");
2083 break;
2084 case 1:
2085 fprintf(outfile," %s_rounding = ", lname);
2086 blocktree(tptr->down, PRINTTOKENS);
2087 fprintf(outfile,";\n");
2088 fprintf(outfile," %s_x%i = ROUND(%s_rounding);\n",
2089 lname,(i/3)+1,lname);
2090 break;
2091 case 2:
2092 fprintf(outfile," %s_y%i = ",lname,(i/3)+1);
2093 blocktree(tptr->down, PRINTTOKENS);
2094 fprintf(outfile,";\n");
2095 j++;
2096 break;
2097 }
2098 i++;
2099 }
2100 tptr = tptr->next;
2101 }
2102 j--;i--;
2103
2104 z[lc++]="%2$s_k1 = 0.0F;";
2105 mz(lc); sprintf(z[lc++],"%s_k%i = 0.0F;", lname,j);
2106
2107 if (j<2)
2108 genex(&lc, wname, "Less than 2 parameters");
2109 if ((i % 3) != 2)
2110 genex(&lc, wname, "Sequence must end with yn.");
2111
2112 else
2113 {
2114 i = 1;
2115 while (i < j)
2116 {
2117 mz(lc); sprintf(z[lc++],"if (%s_x%i > %s_x%i)",
2118 lname,i,lname,i+1);
2119 genex(&lc, wname, "xvals not a non-decreasing sequence");
2120
2121 mz(lc); sprintf(z[lc++],"if (%s_x%i != %s_x%i)",
2122 lname,i,lname,i+1);
2123 z[lc++]="{";
2124
2125 mz(lc); sprintf(z[lc++],"%s_Q = 1.0F/(%s_x%i - %s_x%i);",
2126 lname,lname,i,lname,i+1);
2127
2128 mz(lc); sprintf(z[lc++],
2129 "%s_R = %s_Q*(%s_x%i*%s_x%i - %s_x%i*%s_x%i) - 2.0F*%s_x%i;",
2130 lname,lname,lname,i,lname,i,
2131 lname,i+1,lname,i+1,lname,i);
2132
2133 z[lc++]="if (%2$s_R == 0.0F)";
2134 genex(&lc, wname, "No spline solution for these parameters");
2135
2136 z[lc++]="%2$s_R =1.0F/%2$s_R;";
2137
2138 mz(lc); sprintf(z[lc++],
2139 "%s_S = %s_Q*(%s_x%i*%s_x%i - %s_x%i*%s_x%i) - 2.0F*%s_x%i;",
2140 lname,lname,lname,i,lname,i,
2141 lname,i+1,lname,i+1,lname,i+1);
2142
2143 z[lc++]="if (%2$s_S == 0.0F)";
2144 genex(&lc, wname, "No spline solution for these parameters");
2145
2146 z[lc++]="%2$s_S =1.0F/%2$s_S;";
2147
2148 mz(lc); sprintf(z[lc++],
2149 "%s_a%i = %s_Q*(%s_x%i*%s_x%i*%s_x%i-%s_x%i*%s_x%i*%s_x%i)*(%s_R-%s_S);",
2150 lname,i,lname,
2151 lname,i,lname,i,lname,i,
2152 lname,i+1,lname,i+1,lname,i+1,
2153 lname,lname);
2154
2155 mz(lc); sprintf(z[lc++],
2156 "%s_a%i += -3.0F*(%s_R*%s_x%i*%s_x%i - %s_S*%s_x%i*%s_x%i);",
2157 lname,i,
2158 lname, lname,i,lname,i,
2159 lname, lname,i+1,lname,i+1);
2160
2161 mz(lc); sprintf(z[lc++],"if (%s_a%i==0.0F)",lname,i);
2162 genex(&lc, wname, "No spline solution for these parameters");
2163
2164 mz(lc); sprintf(z[lc++],
2165 "%s_a%i =1.0F/%s_a%i;",
2166 lname,i,lname,i);
2167
2168 mz(lc); sprintf(z[lc++],
2169 "%s_a%i *= %s_Q*(%s_y%i-%s_y%i)*(%s_R-%s_S) - %s_R*%s_k%i + %s_S*%s_k%i;",
2170 lname,i,lname,lname,i,lname,i+1,
2171 lname,lname,lname,lname,i,
2172 lname,lname,i+1);
2173
2174 mz(lc); sprintf(z[lc++],
2175 "%s_b%i = %s_Q*(%s_k%i-%s_k%i)*0.5F;",
2176 lname,i,
2177 lname, lname,i,lname,i+1);
2178 mz(lc); sprintf(z[lc++],
2179 "%s_b%i += - 1.5F*%s_a%i*%s_Q*(%s_x%i*%s_x%i - %s_x%i*%s_x%i);",
2180 lname,i,lname,i,lname,
2181 lname,i,lname,i,lname,i+1,lname,i+1);
2182
2183 mz(lc); sprintf(z[lc++],
2184 "%s_c%i = %s_k%i - 3.0F*%s_a%i*%s_x%i*%s_x%i -2.0F*%s_b%i*%s_x%i;",
2185 lname,i,lname,i,lname,i,lname,i,
2186 lname,i,lname,i,lname,i);
2187
2188 mz(lc); sprintf(z[lc++],
2189 "%s_d%i=%s_y%i-%s_a%i*%s_x%i*%s_x%i*%s_x%i-%s_b%i*%s_x%i*%s_x%i-%s_c%i*%s_x%i;"
2190 ,lname,i,lname,i,lname,i,lname,i
2191 ,lname,i,lname,i,lname,i,lname,i
2192 ,lname,i,lname,i,lname,i);
2193
2194 z[lc++]="}";
2195 i++;
2196 }
2197
2198 }
2199 printwavesymblock2(lc,wname);
2200 break;
2201
2202 }
2203 if (!(strcmp(ident->val,"step")))
2204 {
2205 i = 1;
2206 while (tptr != NULL)
2207 {
2208 if (tptr->ttype == S_EXPR)
2209 {
2210 wavevarinitcheck(tptr);
2211 if ((i % 2) == 1)
2212 {
2213 fprintf(outfile," %s_rounding = ", lname);
2214 blocktree(tptr->down, PRINTTOKENS);
2215 fprintf(outfile,";\n");
2216 fprintf(outfile," %s_x%i = ROUND(%s_rounding);\n",
2217 lname, (i/2)+1, lname);
2218 }
2219 else
2220 {
2221 fprintf(outfile," %s_y%i = ",lname,(i/2));
2222 blocktree(tptr->down, PRINTTOKENS);
2223 fprintf(outfile,";\n");
2224 }
2225 i++;
2226 }
2227 tptr = tptr->next;
2228 }
2229 i--;
2230 if (i % 2 == 0)
2231 genex(&lc, wname, "Not enough parameters");
2232 else
2233 {
2234 i = (i/2) + 1;
2235 while (i >= 2)
2236 {
2237 mz(lc); sprintf(z[lc++],"if (%s_x%i > %s_x%i)",
2238 lname,i-1,lname,i);
2239 genex(&lc, wname, "xvals not a non-decreasing sequence");
2240
2241 i--;
2242 }
2243 z[lc++]="if (%2$s_x1 != 0.0F)";
2244 genex(&lc, wname, "x1 != 0");
2245 }
2246 printwavesymblock2(lc,wname);
2247 break;
2248 }
2249 break;
2250 case 'w':
2251 if (!(strcmp(ident->val,"window")))
2252 {
2253 i = 1;
2254 while (tptr != NULL)
2255 {
2256 if (tptr->ttype == S_EXPR)
2257 {
2258 wavevarinitcheck(tptr);
2259 switch (i) {
2260 case 1:
2261 fprintf(outfile," %s_rounding = ", lname);
2262 blocktree(tptr->down, PRINTTOKENS);
2263 fprintf(outfile,";\n");
2264
2265 fprintf(outfile," %s_type = ROUND(%s_rounding);\n",
2266 lname, lname);
2267 break;
2268 case 2:
2269 fprintf(outfile," %s_p = ",lname);
2270 blocktree(tptr->down, PRINTTOKENS);
2271 fprintf(outfile,";\n");
2272 break;
2273 default:
2274 printf("Error: Too many parameters.\n");
2275 showerrorplace(wname->linenum, wname->filename);
2276 }
2277 i++;
2278 }
2279 tptr = tptr->next;
2280 }
2281 break;
2282 }
2283 break;
2284 default:
2285 break;
2286 }
2287 free(lname);
2288 currblockrate = currblocksafe;
2289 }
2290
2291 extern void samplefilepreamble(sigsym *, int *);
2292
2293 /*********************************************************/
2294 /* adds code common to all tables to wavegenerator */
2295 /*********************************************************/
2296
tablepreamble(sigsym * ident,char * prefix,int mode,int action)2297 void tablepreamble(sigsym * ident, char * prefix, int mode, int action)
2298
2299 {
2300
2301 int lc = 0;
2302 int j;
2303 char * lname = makewstring(ident->val);
2304
2305 tnode * aptr = ident->defnode->down->next->next->next->next->next->down;
2306
2307 z[lc++]= " ";
2308
2309 if (0)
2310 {
2311 z[lc++]= "NT(%1$s).start = 0;";
2312 z[lc++]= "NT(%1$s).end = 0;";
2313 z[lc++]= "NT(%1$s).sr = 0;";
2314 z[lc++]= "NT(%1$s).dint = 0;";
2315 z[lc++]= "NT(%1$s).dfrac = 0;";
2316 z[lc++]= "NT(%1$s).sffl = 0;";
2317 z[lc++]= "NT(%1$s).sfui = 0;";
2318 z[lc++]= "NT(%1$s).dsincr = 0;";
2319 z[lc++]= "NT(%1$s).base = 0;";
2320 z[lc++]= "NT(%1$s).oconst = 0;";
2321 z[lc++]= "NT(%1$s).tend = 0;";
2322 }
2323
2324 z[lc++]= "i = NT(%1$s).len = %2$s_size;";
2325
2326 switch (action) {
2327 case GENILLEGAL:
2328 z[lc++]= "if (i < 1)";
2329 genex(&lc, ident->defnode->down, "Table length < 1");
2330 break;
2331 case GENNUMDATA:
2332 z[lc++]= "if (i == -1) ";
2333 mz(lc); sprintf(z[lc++]," %s_size = i = NT(%s_%s).len = %i;",
2334 lname, prefix,ident->val, tablelistlength(aptr));
2335 z[lc++]= "if (i < 1)";
2336 genex(&lc, ident->defnode->down, "Table length < 1");
2337 break;
2338 case GENSTEP:
2339 z[lc++]= "if (i == -1) ";
2340 mz(lc);sprintf(z[lc++]," %s_size = i = NT(%s_%s).len = %s_x%i;",
2341 lname,prefix,ident->val,lname,
2342 (tablelistlength(aptr)/2)+1);
2343 z[lc++]= "if (i < 1)";
2344 genex(&lc, ident->defnode->down, "Table length < 1");
2345 break;
2346 case GENPAIRS:
2347 z[lc++]= "if (i == -1) ";
2348 mz(lc);sprintf(z[lc++]," %s_size = i = NT(%s_%s).len = %s_x%i;",
2349 lname,prefix,ident->val,lname,
2350 tablelistlength(aptr)/2);
2351 z[lc++]= "if (i < 1)";
2352 genex(&lc, ident->defnode->down, "Table length < 1");
2353 break;
2354 case GENCUBIC:
2355 z[lc++]= "if (i == -1) ";
2356 j = tablelistlength(aptr);
2357 mz(lc);
2358 if (4*(j/4) == j)
2359 sprintf(z[lc++]," %s_size = i = NT(%s_%s).len = %s_x%i;",
2360 lname,prefix,ident->val,
2361 lname,tablelistlength(aptr)/4);
2362 else
2363 sprintf(z[lc++]," %s_size = i = NT(%s_%s).len = %s_infl%i;",
2364 lname,prefix,ident->val,
2365 lname,(tablelistlength(aptr)/4)+1);
2366 z[lc++]= "if (i < 1)";
2367 genex(&lc, ident->defnode->down, "Table length < 1");
2368 break;
2369 case GENSPLINE:
2370 z[lc++]= "if (i == -1) ";
2371 mz(lc);sprintf(z[lc++]," %s_size = i = NT(%s_%s).len = %s_x%i;",
2372 lname, prefix,ident->val,
2373 lname,((tablelistlength(aptr)+1)/3));
2374 z[lc++]= "if (i < 1)";
2375 genex(&lc, ident->defnode->down, "Table length < 1");
2376 break;
2377 case GENBUZZ:
2378 z[lc++]="if ((%2$s_lowharm<0))";
2379 genex(&lc, ident->defnode->down, "Low harm must be >= 0");
2380 z[lc++]="if ((i < 1) && (%2$s_nharm<1))";
2381 genex(&lc, ident->defnode->down, "Buzz size and nharm both < 1");
2382 z[lc++]="if ((i < 1) || (%2$s_nharm<1))";
2383 z[lc++]="{";
2384 z[lc++]=" if (i < 1)";
2385 z[lc++]=" NT(%1$s).len = %2$s_size = i = 2*(%2$s_lowharm + %2$s_nharm);";
2386 z[lc++]=" else";
2387 z[lc++]=" %2$s_nharm = (int)floor(i/2.0 - %2$s_lowharm);";
2388 z[lc++]="}";
2389 z[lc++]="if (((%2$s_acc=fabs(%2$s_rolloff))<1.0F)&&(%2$s_rolloff!=0.0F))";
2390 z[lc++]="{";
2391 z[lc++]= "j = -(int)(17.0F/log(%2$s_acc)) + %2$s_lowharm + 1;";
2392 z[lc++]= "%2$s_nharm = (%2$s_nharm > j) ? j : %2$s_nharm;";
2393 z[lc++]="}";
2394
2395 break;
2396 case GENCONCAT:
2397 z[lc++]= "if (i < 1)";
2398 z[lc++]= "{";
2399 z[lc++]= " i = 0;";
2400 j = tablelistlength(aptr);
2401 while (j >=1)
2402 {
2403 mz(lc); sprintf(z[lc++]," if (AP%i.t == NULL)", j);
2404 genex(&lc, ident->defnode->down, "Can't concat an uninitialized table");
2405 mz(lc); sprintf(z[lc++]," i += AP%i.len;", j);
2406 j--;
2407 }
2408 z[lc++]= " if (i < 1)";
2409 genex(&lc, ident->defnode->down, "Table length < 1");
2410 z[lc++]= " NT(%1$s).len = %2$s_size = i;";
2411 z[lc++]= "}";
2412 break;
2413 default:
2414 internalerror("wtparse.c", "case statement");
2415 }
2416
2417 if (interp == INTERP_SINC)
2418 {
2419 z[lc++]= "NT(%1$s).sffl = 1.0F;";
2420 z[lc++]= "NT(%1$s).sfui = 0x00010000;";
2421 z[lc++]= "NT(%1$s).dsincr = SINC_PILEN;";
2422 }
2423
2424 z[lc++]= "NT(%1$s).stamp = EV(scorebeats);";
2425 z[lc++]= "NT(%1$s).lenf = (float)(i);";
2426 z[lc++]= "NT(%1$s).oconst = EV(ATIME)*((float)i);";
2427 z[lc++]= "if (i>0)";
2428 z[lc++]= "{";
2429 z[lc++]= " NT(%1$s).tend = i - 1;";
2430 z[lc++]= "}";
2431 z[lc++]= "NT(%1$s).t = (float *) malloc((i+1)*sizeof(float));";
2432 z[lc++]= "NT(%1$s).llmem = 1;";
2433 z[lc++]= "i--;";
2434 z[lc++]= " ";
2435 printwavesymblock(lc,ident,prefix);
2436 free(lname);
2437 return;
2438
2439 }
2440
2441
2442 /*~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~*/
2443 /* */
2444 /* Simpler utility functions used by code generation routines. */
2445 /* */
2446 /*______________________________________________________________*/
2447
2448 /*********************************************************/
2449 /* do variable checks for generator execution */
2450 /*********************************************************/
2451
wavevarinitcheck(tnode * tptr)2452 void wavevarinitcheck(tnode * tptr)
2453
2454 {
2455 widthupdate(tptr);
2456 if (truewidth(tptr->width) != 1)
2457 {
2458 while (tptr->down != NULL)
2459 tptr = tptr->down;
2460 printf("Error: Generator arguments must be width 1.\n");
2461 showerrorplace(tptr->linenum, tptr->filename);
2462 }
2463 curropcoderate = ARATETYPE;
2464 currtreerate = UNKNOWN;
2465 rateupdate(tptr);
2466 if (tptr->rate != IRATETYPE)
2467 {
2468 while (tptr->down != NULL)
2469 tptr = tptr->down;
2470 printf("Error: Generators arguments must run at i-rate.\n");
2471 showerrorplace(tptr->linenum, tptr->filename);
2472 }
2473 if ((tptr->vartype == TMAPTYPE)||(tptr->vartype == TABLETYPE))
2474 {
2475 while (tptr->down != NULL)
2476 tptr = tptr->down;
2477 printf("Error: Table(map) an inappropriate argument.\n");
2478 showerrorplace(tptr->linenum, tptr->filename);
2479 }
2480 }
2481
2482 /*********************************************************/
2483 /* computes length of argument list for table (w/o size) */
2484 /*********************************************************/
2485
tablelistlength(tnode * tptr)2486 int tablelistlength(tnode * tptr)
2487
2488 {
2489 int j=0;
2490
2491 tptr = tptr->next;
2492 if (tptr != NULL)
2493 tptr = tptr->next;
2494 while (tptr != NULL)
2495 {
2496 j++;
2497 tptr = tptr->next;
2498 if (tptr != NULL)
2499 tptr = tptr->next;
2500 }
2501 return j;
2502 }
2503
2504 /*********************************************************/
2505 /* creates alias-free local variable name */
2506 /*********************************************************/
2507
makewstring(char * val)2508 char * makewstring(char * val)
2509
2510 {
2511 char * lname;
2512
2513 vmcheck(lname = calloc(strlen(val)+strlen("_sym_") + 1,
2514 sizeof(char)));
2515 strcpy(lname, val);
2516 strcat(lname, "__sym");
2517 return(lname);
2518
2519 }
2520
2521
2522 /*********************************************************/
2523 /* adds aiff/wav sample reading code */
2524 /*********************************************************/
2525
samplefilecode(sigsym * ident,char * prefix,int * lcptr)2526 void samplefilecode(sigsym * ident, char * prefix, int * lcptr)
2527
2528 {
2529 char newval[STRSIZE];
2530 int lc = *lcptr;
2531 sampleinfo * sinfo;
2532 double intdummy;
2533 tnode * sizeptr;
2534 tnode * fileptr;
2535 tnode * skipptr = NULL;
2536 unsigned int size = 0;
2537 int tsize = 0;
2538 unsigned int skip = 0;
2539 int known, currblocksafe;
2540 char * lname = makewstring(ident->val);
2541 char * suffix;
2542 char bytecount;
2543
2544 /* see wtconst.c for regularization of constant size and skip */
2545
2546 sizeptr = ident->defnode->down->next->next->next->next->next->down;
2547 fileptr = sizeptr->next->next;
2548 skipptr = (fileptr->next) ? fileptr->next->next : NULL;
2549
2550 sinfo = (sampleinfo *) fileptr->ibus;
2551
2552 /***********************************************/
2553 /* set variables independent of size and skip */
2554 /***********************************************/
2555
2556 z[lc++]= "NT(%1$s).stamp = EV(scorebeats);";
2557
2558 mz(lc); sprintf(z[lc++], "NT(%s_%s).sr = %i;", prefix, ident->val,
2559 sinfo->srate);
2560
2561 if (reentrant)
2562 {
2563 mz(lc); sprintf(z[lc++], "if (EV(ARATE) == %u.0F)", sinfo->srate);
2564 mz(lc); sprintf(z[lc++], " {");
2565 mz(lc); sprintf(z[lc++], " NT(%s_%s).dint = 1;", prefix, ident->val);
2566 mz(lc); sprintf(z[lc++], " NT(%s_%s).dfrac = 0;", prefix, ident->val);
2567 mz(lc); sprintf(z[lc++], " }");
2568 mz(lc); sprintf(z[lc++], "else");
2569 mz(lc); sprintf(z[lc++], " {");
2570 mz(lc); sprintf(z[lc++], " NT(%s_%s).dfrac = (unsigned int)"
2571 "(4294967296.0*((%u.0/EV(ARATE)) - ((int)(%u.0/EV(ARATE)))));",
2572 prefix, ident->val, sinfo->srate, sinfo->srate);
2573 mz(lc); sprintf(z[lc++], " NT(%s_%s).dint = (unsigned int)(%u.0/EV(ARATE));",
2574 prefix, ident->val, sinfo->srate);
2575 mz(lc); sprintf(z[lc++], " }");
2576 }
2577 else
2578 {
2579 if (srate == sinfo->srate)
2580 {
2581 mz(lc); sprintf(z[lc++], "NT(%s_%s).dint = 1;", prefix, ident->val);
2582 mz(lc); sprintf(z[lc++], "NT(%s_%s).dfrac = 0;", prefix, ident->val);
2583 }
2584 else
2585 {
2586 mz(lc); sprintf(z[lc++], "NT(%s_%s).dfrac = %uU;", prefix, ident->val,
2587 (unsigned int) (4294967296.0*
2588 modf(((double)sinfo->srate)/((double)srate),
2589 &intdummy)));
2590 mz(lc); sprintf(z[lc++], "NT(%s_%s).dint = %uU;", prefix, ident->val,
2591 (unsigned int) intdummy);
2592 }
2593 }
2594
2595 if (interp == INTERP_SINC)
2596 {
2597 if (reentrant)
2598 {
2599 mz(lc); sprintf(z[lc++], "if (EV(ARATE) >= %u.0F)", sinfo->srate);
2600 mz(lc); sprintf(z[lc++], " {");
2601 mz(lc); sprintf(z[lc++], "NT(%s_%s).sffl = 1.0F;", prefix, ident->val);
2602 mz(lc); sprintf(z[lc++], "NT(%s_%s).sfui = 0x00010000;", prefix, ident->val);
2603 mz(lc); sprintf(z[lc++], "NT(%s_%s).dsincr = SINC_PILEN;", prefix, ident->val);
2604 mz(lc); sprintf(z[lc++], " }");
2605 mz(lc); sprintf(z[lc++], "else");
2606 mz(lc); sprintf(z[lc++], " {");
2607 mz(lc); sprintf(z[lc++], " if (SINC_UPMAX*EV(ARATE) > %u.0F)",
2608 sinfo->srate);
2609 mz(lc); sprintf(z[lc++], " NT(%s_%s).sffl = (EV(ARATE)/NT(%s_%s).sr);",
2610 prefix, ident->val, prefix, ident->val);
2611 mz(lc); sprintf(z[lc++], " else");
2612 mz(lc); sprintf(z[lc++], " NT(%s_%s).sffl = (1.0F/SINC_UPMAX);",
2613 prefix, ident->val);
2614 mz(lc); sprintf(z[lc++], " NT(%s_%s).sfui = ((float)(pow(2,16)))*NT(%s_%s).sffl + 0.5F;",
2615 prefix, ident->val, prefix, ident->val);
2616 mz(lc); sprintf(z[lc++], " NT(%s_%s).dsincr = (SINC_PILEN*NT(%s_%s).sfui) >> 16;",
2617 prefix, ident->val, prefix, ident->val);
2618 mz(lc); sprintf(z[lc++], " }");
2619 }
2620 else
2621 {
2622 if (srate >= sinfo->srate)
2623 {
2624 mz(lc); sprintf(z[lc++], "NT(%s_%s).sffl = 1.0F;", prefix, ident->val);
2625 mz(lc); sprintf(z[lc++], "NT(%s_%s).sfui = 0x00010000;", prefix, ident->val);
2626 mz(lc); sprintf(z[lc++], "NT(%s_%s).dsincr = SINC_PILEN;", prefix, ident->val);
2627 }
2628 else
2629 {
2630 if (srate*sinc_upmax > sinfo->srate)
2631 {
2632 mz(lc); sprintf(z[lc++], "NT(%s_%s).sffl = (EV(ARATE)/NT(%s_%s).sr);",
2633 prefix, ident->val, prefix, ident->val);
2634 }
2635 else
2636 {
2637 mz(lc); sprintf(z[lc++], "NT(%s_%s).sffl = (1.0F/SINC_UPMAX);",
2638 prefix, ident->val);
2639 }
2640
2641 mz(lc); sprintf(z[lc++],
2642 "NT(%s_%s).sfui = ((float)(pow(2,16)))*NT(%s_%s).sffl + 0.5F;",
2643 prefix, ident->val, prefix, ident->val);
2644 mz(lc); sprintf(z[lc++],
2645 "NT(%s_%s).dsincr = (SINC_PILEN*NT(%s_%s).sfui) >> 16;",
2646 prefix, ident->val, prefix, ident->val);
2647 }
2648 }
2649 }
2650
2651 if (sinfo->hasbase)
2652 {
2653 mz(lc); sprintf(z[lc++], "NT(%s_%s).base = %s;", prefix, ident->val,
2654 compactfloat(newval, sinfo->base));
2655 }
2656
2657 if (sinfo->hasloop)
2658 {
2659 mz(lc); sprintf(z[lc++], "NT(%s_%s).start = %i;",
2660 prefix, ident->val, sinfo->start);
2661 if (sinfo->end)
2662 {
2663 mz(lc); sprintf(z[lc++], "NT(%s_%s).tend = NT(%s_%s).end = %i;",
2664 prefix, ident->val, prefix, ident->val, sinfo->end);
2665 }
2666 }
2667
2668 /***********************************************/
2669 /* table parameters that depend on size/skip */
2670 /***********************************************/
2671
2672 if ((known = (sizeptr->vol == CONSTANT) &&
2673 ((skipptr == NULL) || (skipptr->vol == CONSTANT))))
2674 {
2675 /******************************/
2676 /* for constant size and skip */
2677 /******************************/
2678
2679 if (skipptr)
2680 skip = atoi(skipptr->down->val);
2681
2682 if (atoi(sizeptr->down->val) <= 0)
2683 {
2684 tsize = 1;
2685 size = sinfo->len - skip;
2686 }
2687 else
2688 size = atoi(sizeptr->down->val);
2689
2690 mz(lc); sprintf(z[lc++],
2691 "NT(%s_%s).lenf = (float)(NT(%s_%s).len = %i);",
2692 prefix,ident->val, prefix, ident->val, size);
2693
2694 mz(lc); sprintf(z[lc++], "NT(%s_%s).oconst = NT(%s_%s).lenf*EV(ATIME);",
2695 prefix,ident->val, prefix, ident->val);
2696
2697 mz(lc); sprintf(z[lc++], "NT(%s_%s).t = (float *)(calloc(%i, %i));",
2698 prefix, ident->val, size + 1, (int)sizeof(float));
2699
2700 if (sinfo->hasloop)
2701 {
2702 if (!(sinfo->end))
2703 {
2704 mz(lc); sprintf(z[lc++], "NT(%s_%s).tend = %i;",
2705 prefix,ident->val, size - 1);
2706 }
2707 }
2708 else
2709 {
2710 mz(lc); sprintf(z[lc++], "NT(%s_%s).tend = %i;",
2711 prefix,ident->val, size - 1);
2712 }
2713 }
2714 else
2715 {
2716
2717 /**********************************/
2718 /* for variable size and/or skip */
2719 /*********************************/
2720
2721 if ((skipptr == NULL) || (skipptr->vol == CONSTANT))
2722 {
2723 if (skipptr)
2724 skip = atoi(skipptr->down->val);
2725
2726 mz(lc); sprintf(z[lc++], "%s_skip = %i;", lname, skip);
2727 }
2728 else
2729 {
2730 currblocksafe = currblockrate;
2731 currblockrate = IRATETYPE;
2732 fprintf(outfile," %s_rounding = ", lname);
2733 blocktree(skipptr->down, PRINTTOKENS);
2734 fprintf(outfile,";\n");
2735 fprintf(outfile," %s_skip = ROUND(%s_rounding);\n",
2736 lname, lname);
2737 fprintf(outfile," if (%s_skip < 0)\n",lname);
2738 fprintf(outfile," %s_skip = 0;\n",lname);
2739 currblockrate = currblocksafe;
2740 }
2741
2742 mz(lc); sprintf(z[lc++],
2743 "NT(%s_%s).lenf = (float)(NT(%s_%s).len = "
2744 "((%s_size <= 0) ? (%i - %s_skip) : %s_size));",
2745 prefix, ident->val, prefix, ident->val, lname,
2746 sinfo->len, lname, lname);
2747
2748 mz(lc); sprintf(z[lc++], "NT(%s_%s).oconst = NT(%s_%s).lenf*EV(ATIME);",
2749 prefix,ident->val, prefix, ident->val);
2750
2751 z[lc++]= "NT(%1$s).t = (float *)(calloc(NT(%1$s).len +1,";
2752 z[lc++]= " sizeof(float)));";
2753
2754 if (sinfo->hasloop)
2755 {
2756 if (!(sinfo->end))
2757 {
2758 z[lc++]="NT(%1$s).tend = NT(%1$s).len - 1;";
2759 }
2760 }
2761 else
2762 {
2763 z[lc++]="NT(%1$s).tend = NT(%1$s).len - 1;";
2764 }
2765 }
2766
2767 /***********************************/
2768 /* code for reading data from file */
2769 /***********************************/
2770
2771 if ((suffix = strrchr(fileptr->val, '.')) && (suffix = strrchr(suffix, '@')))
2772 suffix[0] = '\0';
2773
2774 mz(lc); sprintf(z[lc++], "EV(sfile) = fopen(\"%s\", \"rb\");", fileptr->val);
2775
2776 if (suffix)
2777 suffix[0] = '@';
2778
2779 z[lc++]= "if (EV(sfile) == NULL)";
2780 genex(&lc, ident->defnode->down, "Samplefile not found");
2781
2782 if (known)
2783 {
2784 /* we don't fseek() to simplify signal handling for real-time */
2785
2786 mz(lc); sprintf(z[lc++], "for (i = 0; i < %i; i++)",
2787 sinfo->point + skip*sinfo->framebytes);
2788 z[lc++]= "if (!rread(%2$s_c,1,1,EV(sfile)))";
2789 genex(&lc, ident->defnode->down, "Corrupt samplefile");
2790
2791 mz(lc); sprintf(z[lc++], "for (i=0; i < %i; i++)",
2792 tsize ? size : ((size < (sinfo->len - skip)) ?
2793 size : (sinfo->len - skip)));
2794 z[lc++]= "{";
2795
2796 }
2797 else
2798 {
2799
2800 mz(lc); sprintf(z[lc++], "for (i = 0; i < %i + %i*%s_skip; i++)",
2801 sinfo->point, sinfo->framebytes, lname);
2802 z[lc++]= "if (!rread(%2$s_c,1,1,EV(sfile)))";
2803 genex(&lc, ident->defnode->down, "Corrupt samplefile");
2804
2805 z[lc++]="for (i=0; i < NT(%1$s).len; i++)";
2806 z[lc++]= "{";
2807 mz(lc); sprintf(z[lc++], "if (i >= (%i - %s_skip))",
2808 sinfo->len, lname);
2809 z[lc++]=" break;";
2810 }
2811
2812 mz(lc); sprintf(z[lc++], "if (!rread(%s_c,1,%i,EV(sfile)))",
2813 lname, sinfo->framebytes);
2814 genex(&lc, ident->defnode->down, "Corrupt samplefile");
2815
2816 if (sinfo->wav)
2817 {
2818 if (sinfo->chanpoint > -1)
2819 {
2820 switch (sinfo->numbytes) {
2821 case 3:
2822 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -23))*(";
2823 mz(lc); sprintf(z[lc++], " ((int)(%s_c[%hhi])) + ",
2824 lname, sinfo->chanpoint);
2825 mz(lc); sprintf(z[lc++], " (((int)(%s_c[%hhi])) << 8) +",
2826 lname, sinfo->chanpoint + 1);
2827 mz(lc); sprintf(z[lc++], " (((int)((char)(%s_c[%hhi]))) << 16));",
2828 lname, sinfo->chanpoint + 2);
2829 break;
2830 case 2:
2831 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -15))*(";
2832 mz(lc); sprintf(z[lc++], " ((int)(%s_c[%hhi])) + ",
2833 lname, sinfo->chanpoint);
2834 mz(lc); sprintf(z[lc++], " (((int)((char)(%s_c[%hhi]))) << 8));",
2835 lname, sinfo->chanpoint + 1);
2836 break;
2837 case 1:
2838 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -7))*(";
2839 mz(lc); sprintf(z[lc++], " ((short)(%s_c[%hhi])) - 128); ",
2840 lname, sinfo->chanpoint);
2841 break;
2842 }
2843 }
2844 else
2845 {
2846 switch (sinfo->numbytes) {
2847 case 3:
2848 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -23))*(";
2849
2850 mz(lc); sprintf(z[lc++], " 1.0F/%i.0F)*(",
2851 (int)(sinfo->framebytes/sinfo->numbytes));
2852 break;
2853 case 2:
2854 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -15))*(";
2855
2856 mz(lc); sprintf(z[lc++], " 1.0F/%i.0F)*(",
2857 (int)(sinfo->framebytes/sinfo->numbytes));
2858 break;
2859 case 1:
2860 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -7))*(";
2861
2862 mz(lc); sprintf(z[lc++], " 1.0F/%i.0F)*(",
2863 (int)(sinfo->framebytes/sinfo->numbytes));
2864 break;
2865 }
2866
2867 bytecount = 0;
2868 while (bytecount < sinfo->framebytes)
2869 {
2870 switch (sinfo->numbytes) {
2871 case 3:
2872 mz(lc); sprintf(z[lc++], " %c ((int)(%s_c[%hhi])) + ",
2873 bytecount ? '+' : ' ', lname, bytecount);
2874 mz(lc); sprintf(z[lc++], " (((int)(%s_c[%hhi])) << 8) +",
2875 lname, bytecount + 1);
2876 mz(lc); sprintf(z[lc++], " (((int)((char)(%s_c[%hhi]))) << 16)",
2877 lname, bytecount + 2);
2878 break;
2879 case 2:
2880 mz(lc); sprintf(z[lc++], " %c ((int)(%s_c[%hhi])) + ",
2881 bytecount ? '+' : ' ', lname, bytecount);
2882 mz(lc); sprintf(z[lc++], " (((int)((char)(%s_c[%hhi]))) << 8)",
2883 lname, bytecount + 1);
2884 break;
2885 case 1:
2886 mz(lc); sprintf(z[lc++], " %c ((short)(%s_c[%hhi])) - 128 ",
2887 bytecount ? '+' : ' ', lname, bytecount);
2888 break;
2889 }
2890 bytecount += sinfo->numbytes;
2891 }
2892 z[lc++]= " );";
2893 }
2894 }
2895 else
2896 {
2897 if (sinfo->chanpoint > -1)
2898 {
2899 switch (sinfo->numbytes) {
2900 case 3:
2901 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -23))*(";
2902 mz(lc); sprintf(z[lc++], " ((int)(%s_c[%hhi])) + ",
2903 lname, sinfo->chanpoint + 2);
2904 mz(lc); sprintf(z[lc++], " (((int)(%s_c[%hhi])) << 8) +",
2905 lname, sinfo->chanpoint + 1);
2906 mz(lc); sprintf(z[lc++], " (((int)((char)(%s_c[%hhi]))) << 16));",
2907 lname, sinfo->chanpoint);
2908 break;
2909 case 2:
2910 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -15))*(";
2911 mz(lc); sprintf(z[lc++], " ((int)(%s_c[%hhi])) + ",
2912 lname, sinfo->chanpoint + 1);
2913 mz(lc); sprintf(z[lc++], " (((int)((char)(%s_c[%hhi]))) << 8));",
2914 lname, sinfo->chanpoint);
2915 break;
2916 case 1:
2917 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -7))*(";
2918 mz(lc); sprintf(z[lc++], " ((short)(%s_c[%hhi]))); ",
2919 lname, sinfo->chanpoint);
2920 break;
2921 }
2922 }
2923 else
2924 {
2925 switch (sinfo->numbytes) {
2926 case 3:
2927 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -23))*(";
2928
2929 mz(lc); sprintf(z[lc++], " 1.0F/%i.0F)*(",
2930 (int)(sinfo->framebytes/sinfo->numbytes));
2931 break;
2932 case 2:
2933 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -15))*(";
2934
2935 mz(lc); sprintf(z[lc++], " 1.0F/%i.0F)*(",
2936 (int)(sinfo->framebytes/sinfo->numbytes));
2937 break;
2938 case 1:
2939 z[lc++]= " NT(%1$s).t[i] = ((float)pow(2, -7))*(";
2940
2941 mz(lc); sprintf(z[lc++], " 1.0F/%i.0F)*(",
2942 (int)(sinfo->framebytes/sinfo->numbytes));
2943 break;
2944 }
2945
2946 bytecount = 0;
2947 while (bytecount < sinfo->framebytes)
2948 {
2949 switch (sinfo->numbytes) {
2950 case 3:
2951 mz(lc); sprintf(z[lc++], " %c ((int)(%s_c[%hhi])) + ",
2952 bytecount ? '+': ' ', lname, bytecount + 2);
2953 mz(lc); sprintf(z[lc++], " (((int)(%s_c[%hhi])) << 8) +",
2954 lname, bytecount + 1);
2955 mz(lc); sprintf(z[lc++], " (((int)((char)(%s_c[%hhi]))) << 16)",
2956 lname, bytecount);
2957 break;
2958 case 2:
2959 mz(lc); sprintf(z[lc++], " %c ((int)(%s_c[%hhi])) + ",
2960 bytecount ? '+': ' ', lname, bytecount + 1);
2961 mz(lc); sprintf(z[lc++], " (((int)((char)(%s_c[%hhi]))) << 8)",
2962 lname, bytecount);
2963 break;
2964 case 1:
2965 mz(lc); sprintf(z[lc++], " %c ((short)(%s_c[%hhi])) ",
2966 bytecount ? '+': ' ', lname, bytecount);
2967 break;
2968 }
2969 bytecount += sinfo->numbytes;
2970 }
2971 z[lc++]= " );";
2972 }
2973 }
2974
2975 z[lc++]= "}";
2976
2977 z[lc++]= " fclose(EV(sfile));";
2978 if (known)
2979 {
2980 mz(lc); sprintf(z[lc++], "NT(%s_%s).t[%i] = NT(%s_%s).t[0];",
2981 prefix, ident->val, size, prefix, ident->val);
2982 }
2983 else
2984 {
2985 z[lc++]= "NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
2986 }
2987
2988 *lcptr = lc;
2989 free(lname);
2990
2991 }
2992
2993 /*********************************************************/
2994 /* simplifies random if dist is a constant */
2995 /*********************************************************/
2996
randomconstcode(sigsym * ident,char * prefix,tnode * aptr,int * lcptr)2997 void randomconstcode(sigsym * ident, char * prefix,
2998 tnode * aptr, int * lcptr)
2999
3000 {
3001 int lc = *lcptr;
3002 tnode * distptr = aptr->next->next;
3003 tnode * p1ptr;
3004 tnode * p2ptr;
3005 int dist;
3006
3007 dist = make_int(distptr->down);
3008
3009 if ((dist < 1) || (dist > 5))
3010 {
3011 printf("Error: Illegal random wavetable distribution %i.\n", dist);
3012 showerrorplace(aptr->down->linenum, aptr->down->filename);
3013 }
3014
3015 p1ptr = distptr->next->next;
3016 p2ptr = p1ptr->next ? p1ptr->next->next : NULL;
3017
3018 if ((p2ptr == NULL) && ((dist == 1) || (dist == 2)|| (dist == 4)))
3019 {
3020 printf("Error: Random wavetable distribution %i needs p2.\n", dist);
3021 showerrorplace(aptr->down->linenum, aptr->down->filename);
3022 }
3023
3024 switch (dist) {
3025 case 1:
3026 z[lc++] = " %2$s_c1 = %2$s_p2 - %2$s_p1;";
3027 break;
3028 case 2:
3029 z[lc++] = " %2$s_c1 = %2$s_p2 - %2$s_p1;";
3030 z[lc++] = "if (%2$s_p2 == %2$s_p1)";
3031 genex(&lc, ident->defnode->down, "p1 == p2 (dist 2)");
3032 break;
3033 case 3:
3034 break;
3035 case 4:
3036 z[lc++] = " if (%2$s_p2 <= 0.0F)";
3037 genex(&lc, ident->defnode->down, "p2 <= 0 (dist 4)");
3038 z[lc++] = " %2$s_c1 = (float)sqrt(2*%2$s_p2);";
3039 break;
3040 case 5:
3041 z[lc++] = "j = 0;";
3042 break;
3043 }
3044
3045 z[lc++] = "i = 0;";
3046 z[lc++] = "while (i < %2$s_size)";
3047 z[lc++] = " {";
3048
3049 switch (dist) {
3050 case 1:
3051 z[lc++] = " NT(%1$s).t[i] = %2$s_c1*RMULT*((float)rand()) + %2$s_p1;";
3052 break;
3053 case 2:
3054 z[lc++] = " %2$s_x = RMULT*((float)rand());";
3055 z[lc++] = " %2$s_y = RMULT*((float)rand());";
3056 z[lc++] = " if (%2$s_x > %2$s_y)";
3057 z[lc++] = " NT(%1$s).t[i] = %2$s_c1*%2$s_x + %2$s_p1;";
3058 z[lc++] = " else";
3059 z[lc++] = " NT(%1$s).t[i] = %2$s_c1*%2$s_y + %2$s_p1;";
3060 break;
3061 case 3:
3062 z[lc++] = " NT(%1$s).t[i] = -%2$s_p1*(float)log(RMULT*((float)rand())+1e-45F);";
3063 break;
3064 case 4:
3065 z[lc++] = " NT(%1$s).t[i] = %2$s_p1+%2$s_c1*";
3066 z[lc++] = " (float)sqrt(-2.0F*(float)log(RMULT*((float)rand())+1e-45F))";
3067 z[lc++] = " *(float)cos(6.283185F*RMULT*((float)rand()));";
3068 break;
3069 case 5:
3070 z[lc++] = " NT(%1$s).t[i] = 0;";
3071 z[lc++] = " if (j == 0)";
3072 z[lc++] = " {";
3073 z[lc++] = " j = ROUND(-%2$s_p1*(float)log(RMULT*((float)rand())+1e-45F))+1;";
3074 z[lc++] = " if (i != 0)";
3075 z[lc++] = " NT(%1$s).t[i] = 1.0F;";
3076 z[lc++] = " }";
3077 z[lc++] = " j--;";
3078 break;
3079 }
3080 z[lc++] = " i++;";
3081 z[lc++] = " }";
3082 z[lc++] = " NT(%1$s).t[NT(%1$s).len] = NT(%1$s).t[0];";
3083
3084 *lcptr = lc;
3085
3086 }
3087