Files
epics-base/modules/database/src/ioc/dbStatic/dbYacc.y
Dirk Zimoch 36a8b51d8e CleanupWhitespace
removed spaces at end of line

replaced tabs with spaces
2020-05-20 14:48:09 -07:00

386 lines
9.1 KiB
Plaintext
Raw Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/*************************************************************************\
* Copyright (c) 2009 UChicago Argonne LLC, as Operator of Argonne
* National Laboratory.
* Copyright (c) 2002 The Regents of the University of California, as
* Operator of Los Alamos National Laboratory.
* EPICS BASE is distributed subject to a Software License Agreement found
* in file LICENSE that is included with this distribution.
\*************************************************************************/
%{
static int yyerror();
static int yy_start;
static long pvt_yy_parse(void);
static int yyFailed = 0;
static int yyAbort = 0;
#include "dbLexRoutines.c"
%}
%start database
%union
{
char *Str;
}
%token tokenINCLUDE tokenPATH tokenADDPATH
%token tokenALIAS tokenMENU tokenCHOICE tokenRECORDTYPE
%token tokenFIELD tokenINFO tokenREGISTRAR
%token tokenDEVICE tokenDRIVER tokenLINK tokenBREAKTABLE
%token tokenRECORD tokenGRECORD tokenVARIABLE tokenFUNCTION
%token <Str> tokenSTRING tokenCDEFS
%token jsonNULL jsonTRUE jsonFALSE
%token <Str> jsonNUMBER jsonSTRING jsonBARE
%type <Str> json_value json_object json_array
%type <Str> json_members json_pair json_elements json_string
%%
database: /* empty */
| database_item_list
;
database_item_list: database_item_list database_item
| database_item
;
database_item: include
| path
| addpath
| tokenMENU menu_head menu_body
| tokenRECORDTYPE recordtype_head recordtype_body
| device
| driver
| link
| registrar
| function
| variable
| tokenBREAKTABLE break_head break_body
| tokenRECORD record_head record_body
| tokenGRECORD grecord_head record_body
| alias
;
include: tokenINCLUDE tokenSTRING
{
if(dbStaticDebug>2) printf("include : %s\n",$2);
dbIncludeNew($2); dbmfFree($2);
};
path: tokenPATH tokenSTRING
{
if(dbStaticDebug>2) printf("path : %s\n",$2);
dbPathCmd($2); dbmfFree($2);
};
addpath: tokenADDPATH tokenSTRING
{
if(dbStaticDebug>2) printf("addpath : %s\n",$2);
dbAddPathCmd($2); dbmfFree($2);
};
menu_head: '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("menu_head %s\n",$2);
dbMenuHead($2); dbmfFree($2);
};
menu_body: '{' choice_list '}'
{
if(dbStaticDebug>2) printf("menu_body\n");
dbMenuBody();
};
choice_list: choice_list choice | choice;
choice: tokenCHOICE '(' tokenSTRING ',' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("choice %s %s\n",$3,$5);
dbMenuChoice($3,$5); dbmfFree($3); dbmfFree($5);
}
| include;
recordtype_head: '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("recordtype_head %s\n",$2);
dbRecordtypeHead($2); dbmfFree($2);
};
recordtype_body: '{' '}'
{
if(dbStaticDebug>2) printf("empty recordtype_body\n");
dbRecordtypeEmpty();
}
| '{' recordtype_field_list '}'
{
if(dbStaticDebug>2) printf("recordtype_body\n");
dbRecordtypeBody();
};
recordtype_field_list: recordtype_field_list recordtype_field
| recordtype_field;
recordtype_field: tokenFIELD recordtype_field_head recordtype_field_body
| tokenCDEFS
{
if(dbStaticDebug>2) printf("recordtype_cdef %s", $1);
dbRecordtypeCdef($1); dbmfFree($1);
}
| include ;
recordtype_field_head: '(' tokenSTRING ',' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("recordtype_field_head %s %s\n",$2,$4);
dbRecordtypeFieldHead($2,$4); dbmfFree($2); dbmfFree($4);
};
recordtype_field_body: '{' recordtype_field_item_list '}' ;
recordtype_field_item_list: recordtype_field_item_list recordtype_field_item
| recordtype_field_item;
recordtype_field_item: tokenSTRING '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("recordtype_field_item %s %s\n",$1,$3);
dbRecordtypeFieldItem($1,$3); dbmfFree($1); dbmfFree($3);
}
| tokenMENU '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("recordtype_field_item %s (%s)\n","menu",$3);
dbRecordtypeFieldItem("menu",$3); dbmfFree($3);
};
device: tokenDEVICE '('
tokenSTRING ',' tokenSTRING ',' tokenSTRING ',' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("device %s %s %s %s\n",$3,$5,$7,$9);
dbDevice($3,$5,$7,$9);
dbmfFree($3); dbmfFree($5);
dbmfFree($7); dbmfFree($9);
};
driver: tokenDRIVER '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("driver %s\n",$3);
dbDriver($3); dbmfFree($3);
};
link: tokenLINK '(' tokenSTRING ',' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("link %s %s\n",$3,$5);
dbLinkType($3,$5);
dbmfFree($3); dbmfFree($5);
};
registrar: tokenREGISTRAR '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("registrar %s\n",$3);
dbRegistrar($3); dbmfFree($3);
};
function: tokenFUNCTION '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("function %s\n",$3);
dbFunction($3); dbmfFree($3);
};
variable: tokenVARIABLE '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("variable %s\n",$3);
dbVariable($3,"int"); dbmfFree($3);
}
| tokenVARIABLE '(' tokenSTRING ',' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("variable %s, %s\n",$3,$5);
dbVariable($3,$5); dbmfFree($3); dbmfFree($5);
};
break_head: '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("break_head %s\n",$2);
dbBreakHead($2); dbmfFree($2);
};
break_body : '{' break_list '}'
{
if(dbStaticDebug>2) printf("break_body\n");
dbBreakBody();
};
break_list: break_list ',' break_item
| break_list break_item
| break_item;
break_item: tokenSTRING
{
if(dbStaticDebug>2) printf("break_item tokenSTRING %s\n",$1);
dbBreakItem($1); dbmfFree($1);
};
grecord_head: '(' tokenSTRING ',' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("grecord_head %s %s\n",$2,$4);
dbRecordHead($2,$4,1); dbmfFree($2); dbmfFree($4);
};
record_head: '(' tokenSTRING ',' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("record_head %s %s\n",$2,$4);
dbRecordHead($2,$4,0); dbmfFree($2); dbmfFree($4);
};
record_body: /* empty */
{
if(dbStaticDebug>2) printf("null record_body\n");
dbRecordBody();
}
| '{' '}'
{
if(dbStaticDebug>2) printf("empty record_body\n");
dbRecordBody();
}
| '{' record_field_list '}'
{
if(dbStaticDebug>2) printf("record_body\n");
dbRecordBody();
};
record_field_list: record_field_list record_field
| record_field;
record_field: tokenFIELD '(' tokenSTRING ','
{ BEGIN JSON; } json_value { BEGIN INITIAL; } ')'
{
if(dbStaticDebug>2) printf("record_field %s %s\n",$3,$6);
dbRecordField($3,$6); dbmfFree($3); dbmfFree($6);
}
| tokenINFO '(' tokenSTRING ','
{ BEGIN JSON; } json_value { BEGIN INITIAL; } ')'
{
if(dbStaticDebug>2) printf("record_info %s %s\n",$3,$6);
dbRecordInfo($3,$6); dbmfFree($3); dbmfFree($6);
}
| tokenALIAS '(' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("record_alias %s\n",$3);
dbRecordAlias($3); dbmfFree($3);
}
| include ;
alias: tokenALIAS '(' tokenSTRING ',' tokenSTRING ')'
{
if(dbStaticDebug>2) printf("alias %s %s\n",$3,$5);
dbAlias($3,$5); dbmfFree($3); dbmfFree($5);
};
json_object: '{' '}'
{
$$ = dbmfStrdup("{}");
if (dbStaticDebug>2) printf("json %s\n", $$);
}
| '{' json_members '}'
{
$$ = dbmfStrcat3("{", $2, "}");
dbmfFree($2);
if (dbStaticDebug>2) printf("json %s\n", $$);
};
json_members: json_pair
| json_pair ','
| json_pair ',' json_members
{
$$ = dbmfStrcat3($1, ",", $3);
dbmfFree($1); dbmfFree($3);
if (dbStaticDebug>2) printf("json %s\n", $$);
};
json_pair: json_string ':' json_value
{
$$ = dbmfStrcat3($1, ":", $3);
dbmfFree($1); dbmfFree($3);
if (dbStaticDebug>2) printf("json %s\n", $$);
};
json_string: jsonSTRING
| jsonBARE
{
$$ = dbmfStrcat3("\"", $1, "\"");
dbmfFree($1);
if (dbStaticDebug>2) printf("json %s\n", $$);
};
json_array: '[' ']'
{
$$ = dbmfStrdup("[]");
if (dbStaticDebug>2) printf("json %s\n", $$);
}
| '[' json_elements ']'
{
$$ = dbmfStrcat3("[", $2, "]");
dbmfFree($2);
if (dbStaticDebug>2) printf("json %s\n", $$);
};
json_elements: json_value
| json_value ','
{ /* Retain the trailing ',' so link parser can distinguish a
* 1-element const list from a PV name (commas are illegal)
*/
$$ = dbmfStrcat3($1, ",", "");
dbmfFree($1);
if (dbStaticDebug>2) printf("json %s\n", $$);
};
| json_value ',' json_elements
{
$$ = dbmfStrcat3($1, ",", $3);
dbmfFree($1); dbmfFree($3);
if (dbStaticDebug>2) printf("json %s\n", $$);
};
json_value: jsonNULL { $$ = dbmfStrdup("null"); }
| jsonTRUE { $$ = dbmfStrdup("true"); }
| jsonFALSE { $$ = dbmfStrdup("false"); }
| jsonNUMBER
| json_string
| json_array
| json_object ;
%%
#include "dbLex.c"
static int yyerror(char *str)
{
if (str)
epicsPrintf("Error: %s\n", str);
else
epicsPrintf("Error");
if (!yyFailed) { /* Only print this stuff once */
epicsPrintf(" at or before \"%s\"", yytext);
dbIncludePrint();
yyFailed = TRUE;
}
return(0);
}
static long pvt_yy_parse(void)
{
static int FirstFlag = 1;
long rtnval;
if (!FirstFlag) {
yyAbort = FALSE;
yyFailed = FALSE;
yyreset();
yyrestart(NULL);
}
FirstFlag = 0;
rtnval = yyparse();
if(rtnval!=0 || yyFailed) return(-1); else return(0);
}