/[svn]/linuxsampler/trunk/src/scriptvm/parser.y
ViewVC logotype

Diff of /linuxsampler/trunk/src/scriptvm/parser.y

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 2945 by schoenebeck, Thu Jul 14 00:22:26 2016 UTC revision 2951 by schoenebeck, Fri Jul 15 20:07:47 2016 UTC
# Line 38  Line 38 
38  %token <sValue> STRING  %token <sValue> STRING
39  %token <sValue> IDENTIFIER  %token <sValue> IDENTIFIER
40  %token <sValue> VARIABLE  %token <sValue> VARIABLE
41  %token ON END INIT NOTE DECLARE ASSIGNMENT WHILE IF OR RELEASE AND ELSE  %token ON END INIT NOTE DECLARE ASSIGNMENT WHILE IF OR RELEASE AND ELSE FUNCTION CALL
42  %token BITWISE_OR BITWISE_AND BITWISE_NOT  %token BITWISE_OR BITWISE_AND BITWISE_NOT
43  %token CONTROLLER SELECT CASE TO NOT CONST_ POLYPHONIC MOD  %token CONTROLLER SELECT CASE TO NOT CONST_ POLYPHONIC MOD
44  %token LE GE  %token LE GE
45    
46  %type <nEventHandlers> script eventhandlers  %type <nEventHandlers> script sections
47  %type <nEventHandler> eventhandler  %type <nEventHandler> section eventhandler
48  %type <nStatements> statements body  %type <nStatements> statements opt_statements userfunctioncall
49  %type <nStatement> statement assignment  %type <nStatement> statement assignment
50  %type <nFunctionCall> functioncall  %type <nFunctionCall> functioncall
51  %type <nArgs> args  %type <nArgs> args
# Line 58  Line 58 
58  %%  %%
59    
60  script:  script:
61      eventhandlers  {      sections  {
62          $$ = context->handlers = $1;          $$ = context->handlers = $1;
63      }      }
64    
65  eventhandlers:  sections:
66      eventhandler  {      section  {
67          $$ = new EventHandlers();          $$ = new EventHandlers();
68          $$->add($1);          if ($1) $$->add($1);
69      }      }
70      | eventhandlers eventhandler  {      | sections section  {
71            $$ = $1;
72            if ($2) $$->add($2);
73        }
74    
75    section:
76        function_declaration  {
77            $$ = EventHandlerRef();
78        }
79        | eventhandler  {
80          $$ = $1;          $$ = $1;
         $$->add($2);  
81      }      }
82    
83  eventhandler:  eventhandler:
84      ON NOTE body END ON  {      ON NOTE opt_statements END ON  {
85          if (context->onNote)          if (context->onNote)
86              PARSE_ERR(@2, "Redeclaration of 'note' event handler.");              PARSE_ERR(@2, "Redeclaration of 'note' event handler.");
87          context->onNote = new OnNote($3);          context->onNote = new OnNote($3);
88          $$ = context->onNote;          $$ = context->onNote;
89      }      }
90      | ON INIT body END ON  {      | ON INIT opt_statements END ON  {
91          if (context->onInit)          if (context->onInit)
92              PARSE_ERR(@2, "Redeclaration of 'init' event handler.");              PARSE_ERR(@2, "Redeclaration of 'init' event handler.");
93          context->onInit = new OnInit($3);          context->onInit = new OnInit($3);
94          $$ = context->onInit;          $$ = context->onInit;
95      }      }
96      | ON RELEASE body END ON  {      | ON RELEASE opt_statements END ON  {
97          if (context->onRelease)          if (context->onRelease)
98              PARSE_ERR(@2, "Redeclaration of 'release' event handler.");              PARSE_ERR(@2, "Redeclaration of 'release' event handler.");
99          context->onRelease = new OnRelease($3);          context->onRelease = new OnRelease($3);
100          $$ = context->onRelease;          $$ = context->onRelease;
101      }      }
102      | ON CONTROLLER body END ON  {      | ON CONTROLLER opt_statements END ON  {
103          if (context->onController)          if (context->onController)
104              PARSE_ERR(@2, "Redeclaration of 'controller' event handler.");              PARSE_ERR(@2, "Redeclaration of 'controller' event handler.");
105          context->onController = new OnController($3);          context->onController = new OnController($3);
106          $$ = context->onController;          $$ = context->onController;
107      }      }
108    
109  body:  function_declaration:
110        FUNCTION IDENTIFIER opt_statements END FUNCTION  {
111            const char* name = $2;
112            if (context->functionProvider->functionByName(name)) {
113                PARSE_ERR(@2, (String("There is already a built-in function with name '") + name + "'.").c_str());
114            } else if (context->userFunctionByName(name)) {
115                PARSE_ERR(@2, (String("There is already a user defined function with name '") + name + "'.").c_str());
116            } else {
117                context->userFnTable[name] = $3;
118            }
119        }
120    
121    opt_statements:
122      /* epsilon (empty argument) */  {      /* epsilon (empty argument) */  {
123          $$ = new Statements();          $$ = new Statements();
124      }      }
# Line 126  statement: Line 146  statement:
146      functioncall  {      functioncall  {
147          $$ = $1;          $$ = $1;
148      }      }
149        | userfunctioncall  {
150            $$ = $1;
151        }
152      | DECLARE VARIABLE  {      | DECLARE VARIABLE  {
153          const char* name = $2;          const char* name = $2;
154          //printf("declared var '%s'\n", name);          //printf("declared var '%s'\n", name);
# Line 289  statement: Line 312  statement:
312      | assignment  {      | assignment  {
313          $$ = $1;          $$ = $1;
314      }      }
315      | WHILE '(' expr ')' statements END WHILE  {      | WHILE '(' expr ')' opt_statements END WHILE  {
316          if ($3->exprType() == INT_EXPR) {          if ($3->exprType() == INT_EXPR) {
317              $$ = new While($3, $5);              $$ = new While($3, $5);
318          } else {          } else {
# Line 297  statement: Line 320  statement:
320              $$ = new While(new IntLiteral(0), $5);              $$ = new While(new IntLiteral(0), $5);
321          }          }
322      }      }
323      | IF '(' expr ')' statements ELSE statements END IF  {      | IF '(' expr ')' opt_statements ELSE opt_statements END IF  {
324          $$ = new If($3, $5, $7);          $$ = new If($3, $5, $7);
325      }      }
326      | IF '(' expr ')' statements END IF  {      | IF '(' expr ')' opt_statements END IF  {
327          $$ = new If($3, $5);          $$ = new If($3, $5);
328      }      }
329      | SELECT expr caseclauses END SELECT  {      | SELECT expr caseclauses END SELECT  {
# Line 323  caseclauses: Line 346  caseclauses:
346      }      }
347    
348  caseclause:  caseclause:
349      CASE INTEGER statements  {      CASE INTEGER opt_statements  {
350          $$ = CaseBranch();          $$ = CaseBranch();
351          $$.from = new IntLiteral($2);          $$.from = new IntLiteral($2);
352          $$.statements = $3;          $$.statements = $3;
353      }      }
354      | CASE INTEGER TO INTEGER statements  {      | CASE INTEGER TO INTEGER opt_statements  {
355          $$ = CaseBranch();          $$ = CaseBranch();
356          $$.from = new IntLiteral($2);          $$.from = new IntLiteral($2);
357          $$.to   = new IntLiteral($4);          $$.to   = new IntLiteral($4);
358          $$.statements = $5;          $$.statements = $5;
359      }      }
360    
361    userfunctioncall:
362        CALL IDENTIFIER  {
363            const char* name = $2;
364            StatementsRef fn = context->userFunctionByName(name);
365            if (context->functionProvider->functionByName(name)) {
366                PARSE_ERR(@1, (String("Keyword 'call' must only be used for user defined functions, not for any built-in function like '") + name + "'.").c_str());
367                $$ = StatementsRef();
368            } else if (!fn) {
369                PARSE_ERR(@2, (String("No user defined function with name '") + name + "'.").c_str());
370                $$ = StatementsRef();
371            } else {
372                $$ = fn;
373            }
374        }
375    
376  functioncall:  functioncall:
377      IDENTIFIER '(' args ')'  {      IDENTIFIER '(' args ')'  {
378          const char* name = $1;          const char* name = $1;
379          //printf("function call of '%s' with args\n", name);          //printf("function call of '%s' with args\n", name);
380          ArgsRef args = $3;          ArgsRef args = $3;
381          VMFunction* fn = context->functionProvider->functionByName(name);          VMFunction* fn = context->functionProvider->functionByName(name);
382          if (!fn) {          if (context->userFunctionByName(name)) {
383                PARSE_ERR(@1, (String("Missing 'call' keyword before user defined function name '") + name + "'.").c_str());
384                $$ = new FunctionCall(name, args, NULL);
385            } else if (!fn) {
386              PARSE_ERR(@1, (String("No built-in function with name '") + name + "'.").c_str());              PARSE_ERR(@1, (String("No built-in function with name '") + name + "'.").c_str());
387              $$ = new FunctionCall(name, args, NULL);              $$ = new FunctionCall(name, args, NULL);
388          } else if (args->argsCount() < fn->minRequiredArgs()) {          } else if (args->argsCount() < fn->minRequiredArgs()) {
# Line 371  functioncall: Line 412  functioncall:
412          //printf("function call of '%s' (with empty args)\n", name);          //printf("function call of '%s' (with empty args)\n", name);
413          ArgsRef args = new Args;          ArgsRef args = new Args;
414          VMFunction* fn = context->functionProvider->functionByName(name);          VMFunction* fn = context->functionProvider->functionByName(name);
415          if (!fn) {          if (context->userFunctionByName(name)) {
416                PARSE_ERR(@1, (String("Missing 'call' keyword before user defined function name '") + name + "'.").c_str());
417                $$ = new FunctionCall(name, args, NULL);
418            } else if (!fn) {
419              PARSE_ERR(@1, (String("No built-in function with name '") + name + "'.").c_str());              PARSE_ERR(@1, (String("No built-in function with name '") + name + "'.").c_str());
420              $$ = new FunctionCall(name, args, NULL);              $$ = new FunctionCall(name, args, NULL);
421          } else if (fn->minRequiredArgs() > 0) {          } else if (fn->minRequiredArgs() > 0) {
# Line 386  functioncall: Line 430  functioncall:
430          //printf("function call of '%s' (without args)\n", name);          //printf("function call of '%s' (without args)\n", name);
431          ArgsRef args = new Args;          ArgsRef args = new Args;
432          VMFunction* fn = context->functionProvider->functionByName(name);          VMFunction* fn = context->functionProvider->functionByName(name);
433          if (!fn) {          if (context->userFunctionByName(name)) {
434                PARSE_ERR(@1, (String("Missing 'call' keyword before user defined function name '") + name + "'.").c_str());
435                $$ = new FunctionCall(name, args, NULL);
436            } else if (!fn) {
437              PARSE_ERR(@1, (String("No built-in function with name '") + name + "'.").c_str());              PARSE_ERR(@1, (String("No built-in function with name '") + name + "'.").c_str());
438              $$ = new FunctionCall(name, args, NULL);              $$ = new FunctionCall(name, args, NULL);
439          } else if (fn->minRequiredArgs() > 0) {          } else if (fn->minRequiredArgs() > 0) {

Legend:
Removed from v.2945  
changed lines
  Added in v.2951

  ViewVC Help
Powered by ViewVC