154 lines
3.0 KiB
Plaintext
154 lines
3.0 KiB
Plaintext
%{
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
|
|
extern int yylineno;
|
|
extern char *yytext;
|
|
|
|
extern void yyerror(const char *s);
|
|
extern int yylex();
|
|
extern FILE *yyin;
|
|
|
|
void free_node(char *str) {
|
|
if (str) free(str);
|
|
}
|
|
%}
|
|
|
|
%union {
|
|
char *str;
|
|
}
|
|
|
|
%token <str> IDENTIFIER NUMBER TEXT STRING_LITERAL FLOAT_LITERAL
|
|
%token SHORT_DECLARATION LBRACE RBRACE SEMICOLON ASSIGN LPAREN RPAREN COMMA
|
|
%token VAR FUNC RETURN
|
|
|
|
%token STRING
|
|
%token UINT UINT8 UINT16 UINT32 UINT64
|
|
%token INT INT8 INT16 INT32 INT64
|
|
|
|
%type <str> var_declaration literal type int_types string_types
|
|
%type <str> arg_declaration return_type
|
|
|
|
%%
|
|
|
|
program:
|
|
| program statement
|
|
;
|
|
|
|
statement:
|
|
expr SEMICOLON
|
|
| var_declaration SEMICOLON
|
|
| func_declaration
|
|
| block
|
|
;
|
|
|
|
block:
|
|
LBRACE statements_list RBRACE
|
|
;
|
|
|
|
statements_list:
|
|
| statements_list statement
|
|
;
|
|
|
|
expr:
|
|
// return
|
|
RETURN literal
|
|
| RETURN IDENTIFIER
|
|
//
|
|
| IDENTIFIER ASSIGN literal
|
|
| IDENTIFIER ASSIGN IDENTIFIER
|
|
;
|
|
|
|
int_types:
|
|
UINT { $$ = strdup("uint"); }
|
|
| UINT8 { $$ = strdup("uint8"); }
|
|
| UINT16 { $$ = strdup("uint16"); }
|
|
| UINT32 { $$ = strdup("uint32"); }
|
|
| UINT64 { $$ = strdup("uint64"); }
|
|
| INT { $$ = strdup("int"); }
|
|
| INT8 { $$ = strdup("int8"); }
|
|
| INT16 { $$ = strdup("int16"); }
|
|
| INT32 { $$ = strdup("int32"); }
|
|
| INT64 { $$ = strdup("int64"); }
|
|
;
|
|
|
|
string_types:
|
|
STRING { $$ = strdup("string"); }
|
|
;
|
|
|
|
type:
|
|
int_types { $$ = $1; }
|
|
| string_types { $$ = $1; }
|
|
;
|
|
|
|
literal:
|
|
STRING_LITERAL { $$ = $1; }
|
|
| FLOAT_LITERAL { $$ = $1; }
|
|
| NUMBER { $$ = $1; }
|
|
;
|
|
|
|
// Объявление функций
|
|
arg_declaration:
|
|
IDENTIFIER type {
|
|
$$ = $2; // Возвращаем только тип
|
|
printf("Argument: %s %s\n", $1, $2);
|
|
free_node($1);
|
|
}
|
|
;
|
|
|
|
arg_list:
|
|
| arg_declaration
|
|
| arg_list COMMA arg_declaration
|
|
;
|
|
|
|
// тип
|
|
return_type:
|
|
/* empty */ { $$ = NULL; }
|
|
| type { $$ = $1; }
|
|
;
|
|
|
|
func_declaration:
|
|
FUNC IDENTIFIER LPAREN arg_list RPAREN return_type block {
|
|
printf("Function declaration: %s with return type %s\n", $2, $6 ? $6 : "void");
|
|
free_node($2);
|
|
if ($6) free_node($6);
|
|
}
|
|
;
|
|
//
|
|
|
|
// Объявление переменных
|
|
var_declaration:
|
|
IDENTIFIER SHORT_DECLARATION literal {
|
|
printf("Short declaration: %s := %s\n", $1, $3);
|
|
free_node($1);
|
|
free_node($3);
|
|
}
|
|
| VAR IDENTIFIER type {
|
|
printf("Variable declaration: var %s %s\n", $2, $3);
|
|
free_node($2);
|
|
free_node($3);
|
|
}
|
|
| VAR IDENTIFIER type ASSIGN literal {
|
|
printf("Var with assign declaration: var %s %s = %s\n", $2, $3, $5);
|
|
free_node($2);
|
|
free_node($3);
|
|
free_node($5);
|
|
}
|
|
;
|
|
//
|
|
|
|
%%
|
|
|
|
int main(int argc, char **argv) {
|
|
if (argc > 1) {
|
|
FILE *f = fopen(argv[1], "r");
|
|
if (!f) {
|
|
perror("\033[91mFailed to open file\033[0m");
|
|
return 1;
|
|
}
|
|
yyin = f;
|
|
}
|
|
yyparse();
|
|
return 0;
|
|
} |