4 Ann Hell Ex Machina - Music Software
5 Copyright (C) 2003/2005 Angel Ortega <angel@triptico.com>
7 compiler.y - Scripting language YACC parser
9 This program is free software; you can redistribute it and/or
10 modify it under the terms of the GNU General Public License
11 as published by the Free Software Foundation; either version 2
12 of the License, or (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
23 http://www.triptico.com
34 #include "ss_core.h" /* for ss_debug */
42 void yyerror(char * s
);
44 /* injecting code functions (defined in compiler.l) */
45 int push_code
(char * code
, int times
, int dyn
);
46 int push_code_from_file
(char * file
);
55 static double _length
;
57 static int _transpose
;
58 static double _staccato
;
62 /* parser debugging */
64 #define DEBUGF if(ss_debug)printf
74 static struct _named_block
* _named_blocks
=NULL
;
75 static int _n_named_blocks
=0;
76 static int _named_blocks_size
=0;
86 static struct _group
* _groups
=NULL
;
87 static int _n_groups
=0;
88 static int _groups_size
=0;
97 static struct _mark
* _marks
=NULL
;
98 static int _n_marks
=0;
99 static int _marks_size
=0;
110 static struct _arp
* _arps
=NULL
;
111 static int _n_arps
=0;
112 static int _arps_size
=0;
114 static double _arp_delay
;
115 static int _arp_transpose
;
116 static float _arp_volume
;
117 static int _arp_track
;
119 int compiler_error
=0;
125 ********************/
127 void _c_err
(char * e1
, char * e2
, char * e3
)
128 /* reports an error from the compiler */
131 if
(e1
!= NULL
) printf
(" %s", e1
);
132 if
(e2
!= NULL
) printf
(" %s", e2
);
133 if
(e3
!= NULL
) printf
(" %s", e3
);
134 printf
(" in line %d\n", yyline
);
140 static void _forward
(void)
141 /* moves forward current time by current length */
143 /* just add current length to time cursor */
144 _cur_time
+= _length
;
146 /* quantizations could be done here */
152 static int _set_named_block
(char * name
, char * block
)
153 /* sets a named block */
157 /* find first if block is previously defined */
158 for
(n
=0;n
< _n_named_blocks
;n
++)
160 if
(strcmp
(name
, _named_blocks
[n
].name
) == 0)
162 free
(_named_blocks
[n
].block
);
167 if
(n
== _n_named_blocks
)
169 /* need to expand? */
170 if
(_n_named_blocks
== _named_blocks_size
)
172 _named_blocks_size
+= 4;
174 _named_blocks
=(struct _named_block
*)
175 realloc
(_named_blocks
,
177 sizeof
(struct _named_block
));
183 strncpy
(_named_blocks
[n
].name
, name
, sizeof
(_named_blocks
[n
].name
));
184 _named_blocks
[n
].block
=block
;
190 static void _insert_named_block
(char * name
)
191 /* inserts a named block */
195 for
(n
=0;n
< _n_named_blocks
;n
++)
197 if
(strcmp
(name
, _named_blocks
[n
].name
) == 0)
199 push_code
(_named_blocks
[n
].block
, 1, 0);
204 _c_err
("block-not-found", name
, NULL
);
208 static int _insert_file
(char * filename
)
210 if
(!push_code_from_file
(filename
))
212 _c_err
("script-not-found", filename
, NULL
);
222 static int _push_group
(void)
223 /* starts a new group of notes */
225 if
(_n_groups
== _groups_size
)
229 _groups
=(struct _group
*) realloc
(_groups
,
230 _groups_size
* sizeof
(struct _group
));
233 _groups
[_n_groups
].start
=_cur_time
;
234 _groups
[_n_groups
].gliss
=0.0;
235 _groups
[_n_groups
].max
=0.0;
243 static int _next_group_part
(void)
248 _c_err
("missing-start-of-group", NULL
, NULL
);
252 /* store maximum frame */
253 if
(_groups
[_n_groups
- 1].max
< _cur_time
)
254 _groups
[_n_groups
- 1].max
=_cur_time
;
256 /* add glissando delay */
257 _groups
[_n_groups
- 1].gliss
+= _gliss
;
260 _cur_time
=_groups
[_n_groups
- 1].start
+ _groups
[_n_groups
- 1].gliss
;
266 static int _pop_group
(void)
267 /* finishes a group, moving the frame to the end of the longer part */
271 _c_err
("missing-start-of-group", NULL
, NULL
);
277 _cur_time
=_groups
[_n_groups
].max
;
285 static void _add_mark
(char * name
)
286 /* creates a new mark */
288 if
(_n_marks
== _marks_size
)
292 _marks
=(struct _mark
*) realloc
(_marks
,
293 _marks_size
* sizeof
(struct _mark
));
296 strncpy
(_marks
[_n_marks
].name
, name
, sizeof
(_marks
[_n_marks
].name
));
297 _marks
[_n_marks
].time
=_cur_time
;
303 static void _find_mark
(char * name
, int set
)
304 /* finds a mark by name, optionally moving time cursor there */
308 for
(n
=0;n
< _n_marks
;n
++)
310 if
(strcmp
(_marks
[n
].name
, name
) == 0)
314 if
(_cur_time
> _marks
[n
].time
)
315 _c_err
("mark-overpassed", name
, NULL
);
317 _cur_time
=_marks
[n
].time
;
320 if
(_cur_time
!= _marks
[n
].time
)
321 _c_err
("mark-mismatch", name
, NULL
);
327 _c_err
("mark-not-found", name
, NULL
);
333 static void _arp_default
(void)
334 /* resets arpeggiator values to the default ones */
343 static void _add_arp
(void)
344 /* adds an arpeggiator note */
346 /* if the note is exactly the same, do nothing */
347 if
(_arp_delay
== 0.0 && _arp_transpose
== 0 &&
348 _arp_volume
== 1.0 && _arp_track
== _track
)
351 if
(_n_arps
== _arps_size
)
355 _arps
=(struct _arp
*) realloc
(_arps
,
356 _arps_size
* sizeof
(struct _arp
));
359 _arps
[_n_arps
].delay
=_arp_delay
;
360 _arps
[_n_arps
].transpose
=_arp_transpose
;
361 _arps
[_n_arps
].volume
=_arp_volume
;
362 _arps
[_n_arps
].track
=_arp_track
;
371 static void _add_note_event
(int note
)
372 /* adds a note event */
378 /* calculate the note */
379 np
=note
+ _transpose
+ (_octave
* 12);
381 /* is note out of range? */
382 if
(np
< 0 || np
> 127)
384 _c_err
("note-out-of-range", NULL
, NULL
);
388 e.note.type
=SONG_EV_NOTE
;
389 e.note.time
=_cur_time
;
390 e.note.trk_id
=_track
;
392 e.note.len
=_length
* _staccato
;
397 printf
("Note(%d): %lf %d %lf %lf\n",
398 _track
, _cur_time
, np
, _length
, _volume
);
400 /* add arpeggiator repetitions */
401 for
(n
=0;n
< _n_arps
;n
++)
403 e.note.time
=_cur_time
+ _arps
[n
].delay
;
404 e.note.trk_id
=_arps
[n
].track
;
405 e.note.note
=np
+ _arps
[n
].transpose
;
406 e.note.vol
=_volume
* _arps
[n
].volume
;
413 static void _add_tempo_event
(int trk_id
, double tempo
)
417 e.tempo.type
=SONG_EV_TEMPO
;
418 e.tempo.time
=_cur_time
;
419 e.tempo.trk_id
=trk_id
;
425 static void _add_meter_event
(int trk_id
, int num
, int den
)
429 e.meter.type
=SONG_EV_METER
;
430 e.meter.time
=_cur_time
;
431 e.meter.trk_id
=trk_id
;
437 static void _add_measure_event
(void)
441 e.generic.type
=SONG_EV_MEASURE
;
442 e.generic.time
=_cur_time
;
448 static void _add_ss_sustain_event
(double sustain
)
452 e.ss_sustain.type
=SONG_EV_SS_SUSTAIN
;
453 e.ss_sustain.time
=_cur_time
;
454 e.ss_sustain.trk_id
=_track
;
455 e.ss_sustain.sustain
=sustain
;
461 static void _add_ss_wav_event
(char * wav_file
, int base
, int min
, int max
,
462 double loop_start
, double loop_end
)
466 e.ss_wav.type
=SONG_EV_SS_WAV
;
467 e.ss_wav.time
=_cur_time
;
468 e.ss_wav.trk_id
=_track
;
469 e.ss_wav.file
=wav_file
;
473 e.ss_wav.loop_start
=loop_start
;
474 e.ss_wav.loop_end
=loop_end
;
479 static void _add_ss_pat_event
(char * pat_file
)
483 e.ss_pat.type
=SONG_EV_SS_PAT
;
484 e.ss_pat.time
=_cur_time
;
485 e.ss_pat.trk_id
=_track
;
486 e.ss_pat.file
=pat_file
;
492 static void _add_ss_eff_event
(int type
, int channel
, double size
, float gain
,
493 double depth
, double freq
, double phase
, float initial
, float final
)
498 e.ss_eff.time
=_cur_time
;
499 e.ss_eff.trk_id
=_track
;
500 e.ss_eff.channel
=channel
;
503 e.ss_eff.depth
=depth
;
505 e.ss_eff.phase
=phase
;
506 e.ss_eff.initial
=initial
;
507 e.ss_eff.final
=final
;
513 static void add_midi_channel_event
(int channel
)
517 e.midi_channel.type
=SONG_EV_MIDI_CHANNEL
;
518 e.midi_channel.time
=_cur_time
;
519 e.midi_channel.trk_id
=_track
;
520 e.midi_channel.channel
=channel
;
526 static void add_midi_program_event
(int program
)
530 e.midi_program.type
=SONG_EV_MIDI_PROGRAM
;
531 e.midi_program.time
=_cur_time
;
532 e.midi_program.trk_id
=_track
;
533 e.midi_program.program
=program
;
539 static void _init_track
(void)
540 /* sets the default values for a new track */
550 /* groups should not cross track boundaries */
553 /* reset arpeggiator */
567 %token
<i
> P_INTEGER S_INTEGER
568 %token
<d
> P_REAL S_REAL
569 %token
<i
> NOTE_P NOTE_T3 NOTE_T5
570 %token
<p
> NEW_MARK GOTO_MARK ASSERT_MARK
572 %token
<p
> BLOCK BLK_ASSIGN BLK_INSERT FILE_INSERT
575 %token
<i
> XC_MSECS XC_ABSNOTE
577 %token SS_SEP SS_WAV SS_LOOP_WAV SS_PAT SS_SUSTAIN
578 %token SS_EFF_DELAY SS_EFF_ECHO SS_EFF_COMB SS_EFF_ALLPASS
579 %token SS_EFF_FLANGER SS_EFF_WOBBLE SS_EFF_SQWOBBLE SS_EFF_FADER SS_EFF_REVERB
581 %token MIDI_CHANNEL MIDI_PROGRAM MIDI_GENERIC
583 %type
<i
> integer note note_pitch rest
584 %type
<d
> real p_number number note_length
586 %type
<d
> arp_list arp_note
611 /* absolute octave */
615 /* relative octave */
619 /* absolute volume */
623 /* absolute volume */
627 /* relative volume */
628 _volume
+= (float)$2;
644 /* group delimiter */
657 /* measure mark event */
658 _add_measure_event
();
682 _add_tempo_event
(-1, $2);
684 |
'M' P_INTEGER
'/' P_INTEGER
{
685 /* meter (time signature) setting */
686 _add_meter_event
(-1, $2, $4);
689 | BLOCK
'*' P_INTEGER
{
691 push_code
($1, $3, 1);
695 _set_named_block
($2, $1);
698 /* insert named block */
699 _insert_named_block
($1);
713 P_INTEGER
{ $$
= $1; }
714 | S_INTEGER
{ $$
= $1; }
719 | S_REAL
{ $$
= $1; }
723 P_INTEGER
{ $$
= (double) $1; }
724 | P_REAL
{ $$
= $1; }
728 integer
{ $$
= (double) $1; }
733 note_pitch
{ $$
= $1; }
734 | note note_length
{ $$
= $1; _length
=$2; }
735 | note
'~' number
{ $$
= $1; DEBUGF
("imm volume: %lf\n", $3); }
740 | note_pitch
'&' { $$
= $1 - 1; }
741 | note_pitch
'#' { $$
= $1 + 1; }
742 | note_pitch
'\'' { $$
= $1 + 12; }
743 | note_pitch
',' { $$
= $1 - 12; }
747 P_INTEGER
{ $$
= 1 / (double) $1; }
748 | note_length NOTE_T3
{ $$
= $1 * 2.0 / 3.0; }
749 | note_length NOTE_T5
{ $$
= $1 * 4.0 / 5.0; }
750 | note_length
'*' p_number
{ $$
= $1 * $3; }
751 | note_length
'.' { $$
= $1 * 1.5; }
757 /* rest with length */
764 /* empty arpeggiator */
773 /* first arpeggiator note */
777 | arp_list
',' arp_note
{
778 /* rest of arpeggiator notes */
785 /* arpeggiator delay */
788 | arp_note
'~' number
{
789 /* arpeggiator volume */
790 _arp_volume
=(float)$3;
792 | arp_note S_INTEGER
{
793 /* arpeggiator transpose */
796 | arp_note
'@' P_INTEGER
{
797 /* arpeggiator track */
803 P_INTEGER
{ $$
= $1; }
804 | XC_ABSNOTE
{ $$
= $1; }
808 SS_WAV XC_STR xc_absnote xc_absnote xc_absnote
{
810 _add_ss_wav_event
($2, $3, $4, $5, -1.0, 0.0);
812 | SS_WAV XC_STR xc_absnote xc_absnote xc_absnote number number
{
813 /* load .wav file, with loop boundaries */
814 _add_ss_wav_event
($2, $3, $4, $5, $6, $7);
818 _add_ss_pat_event
($2);
820 | SS_SUSTAIN XC_MSECS
{
822 _add_ss_sustain_event
($2);
824 | SS_EFF_DELAY integer XC_MSECS
{
826 _add_ss_eff_event
(SONG_EV_SS_EFF_DELAY
,
827 $2, $3, 0, 0, 0, 0, 0, 0);
830 | SS_EFF_ECHO integer XC_MSECS number
{
832 _add_ss_eff_event
(SONG_EV_SS_EFF_ECHO
,
833 $2, $3, $4, 0, 0, 0, 0, 0);
836 | SS_EFF_COMB integer XC_MSECS number
{
838 _add_ss_eff_event
(SONG_EV_SS_EFF_COMB
,
839 $2, $3, $4, 0, 0, 0, 0, 0);
842 | SS_EFF_ALLPASS integer XC_MSECS number
{
844 _add_ss_eff_event
(SONG_EV_SS_EFF_ALLPASS
,
845 $2, $3, $4, 0, 0, 0, 0, 0);
848 | SS_EFF_FLANGER integer XC_MSECS number XC_MSECS number number
{
850 _add_ss_eff_event
(SONG_EV_SS_EFF_FLANGER
,
851 $2, $3, $4, $5, $6, $7, 0, 0);
854 | SS_EFF_WOBBLE integer number number
{
856 _add_ss_eff_event
(SONG_EV_SS_EFF_WOBBLE
,
857 $2, 0, 0, 0, $3, $4, 0, 0);
860 | SS_EFF_SQWOBBLE integer number number
{
861 /* square wobble effect */
862 _add_ss_eff_event
(SONG_EV_SS_EFF_SQWOBBLE
,
863 $2, 0, 0, 0, $3, $4, 0, 0);
866 | SS_EFF_FADER integer XC_MSECS number number
{
868 _add_ss_eff_event
(SONG_EV_SS_EFF_FADER
,
869 $2, $3, 0, 0, 0, 0, $4, $5);
872 | SS_EFF_REVERB integer
{
874 _add_ss_eff_event
(SONG_EV_SS_EFF_REVERB
,
875 $2, 0, 0, 0, 0, 0, 0, 0);
878 | MIDI_CHANNEL integer
{
880 add_midi_channel_event
($2);
883 | MIDI_PROGRAM integer
{
885 add_midi_program_event
($2);
891 void yyerror(char * s
)
893 _c_err
(s
, NULL
, NULL
);
901 push_code
("!this-is-a-mark", 1, 0);
902 push_code
("< c1 ; e& ; g>", 1, 0);
903 push_code
("^this-is-a-mark", 1, 0);
904 push_code
("x4,2-1,2.+4", 1, 0);
905 push_code
("a b'' c,, ", 1, 0);
906 push_code
("v0.1 (d8 v+0.1)*10", 1, 0);
907 push_code
("t1 t-2 t+3", 1, 0);
908 push_code
("{ fader -1 100ms 0 1 } r r4. z2 `room_kit.ahs` o4 o+1 o-2 ", 1, 0);
909 push_code
("{ sustain 100ms }", 1, 0);
910 push_code
("T120.0 M4/4 z8 abcde T80 (edcba)=drum1 $drum1 $drum1 ((a&b)*3 (cd)*2)*10", 2, 0);
914 printf
("Exiting main...\n");
919 static void compile_startup
(void)
925 /* default settings */
926 _add_tempo_event
(-2, 120.0);
927 _add_meter_event
(-2, 4, 4);
932 int compile
(char * code
)
936 push_code
(code
, 1, 0);
938 return
(yyparse() + compiler_error
);
942 int compile_file
(char * file
)
946 if
(_insert_file
(file
))
949 return
(yyparse() + compiler_error
);