/* $Id$ */ /* --- START LICENSE --- */ /* -------------------------------------------------------------------------- */ /* DataWorks - Simple DBMS */ /* -------------------------------------------------------------------------- */ /* Copyright (c) 2024 Crabware. */ /* Copyright (c) 2024 pnsk-lab. */ /* Redistribution and use in source and binary forms, with or without modific */ /* ation, are permitted provided that the following conditions are met: */ /* 1. Redistributions of source code must retain the above copyright noti */ /* ce, this list of conditions and the following disclaimer. */ /* 2. Redistributions in binary form must reproduce the above copyright n */ /* otice, this list of conditions and the following disclaimer in the documen */ /* tation and/or other materials provided with the distribution. */ /* 3. Neither the name of the copyright holder nor the names of its contr */ /* ibutors may be used to endorse or promote products derived from this softw */ /* are without specific prior written permission. */ /* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS */ /* " AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, TH */ /* E IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPO */ /* SE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS */ /* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CON */ /* SEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITU */ /* TE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPT */ /* ION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, S */ /* TRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN AN */ /* Y WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY */ /* OF SUCH DAMAGE. */ /* -------------------------------------------------------------------------- */ /* --- END LICENSE --- */ %{ #include "grammersym.h" #include %} %token IDENTIFIER STRING NUMBER SPACE COMMENT LOGICAL %start command %union { struct Node { char* string; char* ident; int errnum; char type; double number; unsigned char logical; struct Node** nodes; void* result; } node; } %{ void parser_process(struct Node* node); char* __dw_strdup(const char* a); double __dw_atof(const char* str); extern const char* yytext; %} %% argument : STRING { $$.string = $1.string; $$.nodes = $1.nodes; $$.ident = $1.ident; $$.number = $1.number; $$.type = $1.type; $$.logical = $1.logical; } | NUMBER { $$.string = $1.string; $$.nodes = $1.nodes; $$.ident = $1.ident; $$.number = $1.number; $$.type = $1.type; $$.logical = $1.logical; } | LOGICAL { $$.string = $1.string; $$.nodes = $1.nodes; $$.ident = $1.ident; $$.number = $1.number; $$.type = $1.type; $$.logical = $1.logical; } | command { $$ = $1; } ; single_argument : SPACE argument SPACE { $$.string = $2.string; $$.nodes = $2.nodes; $$.ident = $2.ident; $$.number = $2.number; $$.type = $2.type; $$.logical = $2.logical; } | SPACE argument { $$.string = $2.string; $$.nodes = $2.nodes; $$.ident = $2.ident; $$.number = $2.number; $$.type = $2.type; $$.logical = $2.logical; } | argument SPACE { $$.string = $1.string; $$.nodes = $1.nodes; $$.ident = $1.ident; $$.number = $1.number; $$.type = $1.type; $$.logical = $1.logical; } | argument { $$.string = $1.string; $$.nodes = $1.nodes; $$.ident = $1.ident; $$.number = $1.number; $$.type = $1.type; $$.logical = $1.logical; } ; arguments : single_argument { $$.nodes = malloc(sizeof(*$$.nodes) * 2); $$.nodes[0] = malloc(sizeof($$)); $$.nodes[0]->nodes = NULL; $$.nodes[0]->ident = NULL; $$.nodes[0]->string = NULL; $$.nodes[0]->logical = $1.logical; $$.nodes[0]->number = $1.number; $$.nodes[0]->type = $1.type; if($1.ident != NULL) $$.nodes[0]->ident = __dw_strdup($1.ident); if($1.string != NULL) $$.nodes[0]->string = __dw_strdup($1.string); if($1.nodes != NULL) $$.nodes[0]->nodes = $1.nodes; $$.nodes[1] = NULL; } | arguments ',' single_argument { struct Node** old_nodes = $$.nodes; int i; for(i = 0; old_nodes[i] != NULL; i++); $$.nodes = malloc(sizeof(*$$.nodes) * (i + 2)); for(i = 0; old_nodes[i] != NULL; i++) $$.nodes[i] = old_nodes[i]; $$.nodes[i] = malloc(sizeof($$)); $$.nodes[i]->nodes = NULL; $$.nodes[i]->ident = NULL; $$.nodes[i]->string = NULL; $$.nodes[i]->logical = $3.logical; $$.nodes[i]->number = $3.number; $$.nodes[i]->type = $3.type; if($3.ident != NULL) $$.nodes[i]->ident = __dw_strdup($3.ident); if($3.string != NULL) $$.nodes[i]->string = __dw_strdup($3.string); if($3.nodes != NULL) $$.nodes[i]->nodes = $3.nodes; $$.nodes[i + 1] = NULL; free(old_nodes); } | SPACE | ; ; command : IDENTIFIER SPACE '(' arguments ')' { $$.string = NULL; $$.ident = $1.ident; $$.nodes = $4.nodes; $$.type = $1.type; } | IDENTIFIER '(' arguments ')' { $$.string = NULL; $$.ident = $1.ident; $$.nodes = $3.nodes; $$.type = $1.type; } | COMMENT { $$.string = NULL; $$.ident = NULL; $$.nodes = NULL; $$.type = 'C'; } ; %% #if defined(YYBISON) const char* yaccver = "GNU Bison " YYBISON_VERSION; #error "GNU Bison does not work. Use Berkeley Yacc." #elif defined(YYBYACC) #define XSTR(x) #x #define STR(x) XSTR(x) const char* yaccver = "Berkeley Yacc " STR(YYMAJOR) "." STR(YYMINOR); #else const char* yaccver = "Unknown"; #endif