Untitled
unknown
plain_text
7 months ago
19 kB
1
Indexable
Never
%{ #include <stdio.h> #include <stdlib.h> #include <string.h> #include "bengisuozdemir-hw3.h" void yyerror (const char *s) {return;} ExprNode * makeExpressionNodeFromIdent(IdentNode); ExprNode * makeExpressionNodeFromNumber(NumberNode); ExprNode * sumExpr(ExprNode *, ExprNode *); ExprNode * mulExpr(ExprNode *, ExprNode *); ExprNode * divExpr(ExprNode *, ExprNode *); ExprNode * subExpr(ExprNode *, ExprNode *); void assign(ExprNode *, ExprNode *); int checkIdentifier(ExprNode *); ExprNode ** expressions; int expressionsSize = 100; int exprIndex = 0; int error = 0; char ** errors; int errorSize = 100; int errorIndex = 0; %} %union{ IdentNode identNode; NumberNode numberNode; ExprNode * exprNodePtr; int lineNum; } %token <lineNum> tASSIGN %token <identNode> tIDENT %token <numberNode> tNUMBER %token tPLUS tSUB tMUL tDIV tSTRING tPRINT tGET tSET tFUNCTION tRETURN tEQUALITY tIF tGT tLT tGEQ tLEQ tINC tDEC %start prog %type <exprNodePtr> expr %% prog: '[' stmtlst ']' ; stmtlst:| |stmtlst stmt |summationStatement stmtlst |multiplicationStatement stmtlst |divisionStatement stmtlst |subtractionStatement stmtlst |assignmentStatement stmtlst ; stmt: assignmentStatement | if | print | unaryOperation | expr | returnStmt ; /*implemet other operations here*/ summationStatement :'[' tPLUS ',' expr ',' expr ']'{ sumExpr($4, $6); } ; multiplicationStatement :'[' tMUL ',' expr ',' expr ']'{ mulExpr($4, $6); } ; divisionStatement : '[' tDIV ',' expr ',' expr ']'{ divExpr($4, $6); } ; subtractionStatement : '[' tSUB ',' expr ',' expr ']'{ subExpr($4, $6); } ; /*implement set here*/ assignmentStatement : '[' tSET ',' expr ',' expr ']' { assign($4, $6); } ; expr : tIDENT { $$ = makeExpressionNodeFromIdent($1); } | tNUMBER{ $$ = makeExpressionNodeFromNumber($1); } | getExpr | function | operation | condition ; getExpr: '[' tGET ',' tIDENT ',' '[' exprList ']' ']' | '[' tGET ',' tIDENT ',' '[' ']' ']' | '[' tGET ',' tIDENT ']' ; setStmt: '[' tSET ',' tIDENT ',' expr ']' ; if: '[' tIF ',' condition ',' '[' stmtlst ']' ']' | '[' tIF ',' condition ',' '[' stmtlst ']' '[' stmtlst ']' ']' ; print: '[' tPRINT ',' expr ']' ; operation: summationStatement | multiplicationStatement | divisionStatement | subtractionStatement ; unaryOperation: '[' tINC ',' tIDENT ']' | '[' tDEC ',' tIDENT ']' ; function: '[' tFUNCTION ',' '[' parametersList ']' ',' '[' stmtlst ']' ']' | '[' tFUNCTION ',' '[' ']' ',' '[' stmtlst ']' ']' ; condition: '[' tEQUALITY ',' expr ',' expr ']' | '[' tGT ',' expr ',' expr ']' | '[' tLT ',' expr ',' expr ']' | '[' tGEQ ',' expr ',' expr ']' | '[' tLEQ ',' expr ',' expr ']' ; returnStmt: '[' tRETURN ',' expr ']' | '[' tRETURN ']' ; parametersList: parametersList ',' tIDENT | tIDENT ; exprList: exprList ',' expr | expr ; %% ExprNode * makeExpressionNodeFromIdent(IdentNode ident){ ExprNode * newNode = (ExprNode *)malloc(sizeof(ExprNode)); newNode->identifier = ident.value; newNode->value = -1; newNode->lineNum = ident.lineNum; printf("identifier: %d", newNode->identifier) return newNode; } ExprNode * makeExpressionNodeFromNumber(NumberNode number){ ExprNode * newNode = (ExprNode *)malloc(sizeof(ExprNode)); newNode->identifier = NULL; newNode->value = atoi(number.value); newNode->lineNum = number.lineNum; return newNode; } ExprNode * sumExpr(ExprNode * expr1, ExprNode * expr2){ int expr_id1 = checkIdentifier(expr1); int expr_id2 = checkIdentifier(expr2); //int result_id = checkIdentifier(expr); ExprNode * expr = (ExprNode *)malloc(sizeof(ExprNode)); expr->identifier = NULL; expr->lineNum = expr2->lineNum; //printf("Result id %d\n", result_id); //int result_id = checkIdentifier(expr); printf("exper_id1: %d", expr_id1) printf("exper_id2: %d", expr_id2) if(expr_id1 >= -1 && expr_id2 >= -1 ){ if(expr_id1 >= 0 || expr_id2 >= 0) { if(expr_id1 >= 0) { expr1 = expressions[expr_id1]; printf("expr1: %d", expr1) } if(expr_id2 >= 0) { expr2 = expressions[expr_id2]; printf("expr2: %d", expr2) } expr->value = expr1->value + expr2->value; printf("expr: %d", expr) printf("expr->value: %d", expr->value) PLUSExpressionToList(expr); } if(expr_id1 == -1 && expr_id2 == -1){ //expressions have num token expr->value = expr1->value + expr2->value; PLUSExpressionToList(expr); } else{ error = 1; char * src = "ERROR at line %d: Assigment to number is invalid\n"; char * dest = (char *)malloc(strlen(src) + expr->lineNum + 10); sprintf(dest, src, expr->lineNum); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } } else{ error = 1; if(expr_id1 == -2) { char * src = "ERROR at line %d: %s is undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr1->identifier) + expr1->lineNum + 10); sprintf(dest, src, expr1->lineNum, expr1->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } if(expr_id2 == -2) { char * src = "ERROR at line %d: %s is undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr2->identifier) + expr2->lineNum + 10); sprintf(dest, src, expr2->lineNum, expr2->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } return NULL; } } ExprNode * mulExpr(ExprNode * expr1, ExprNode * expr2){ int expr_id1 = checkIdentifier(expr1); int expr_id2 = checkIdentifier(expr2); //int result_id = checkIdentifier(expr); ExprNode * expr = (ExprNode *)malloc(sizeof(ExprNode)); expr->identifier = NULL; expr->lineNum = expr2->lineNum; //printf("Result id %d\n", result_id); //int result_id = checkIdentifier(expr); if(expr_id1 >= -1 && expr_id2 >= -1 ){ if(expr_id1 >= 0 || expr_id2 >= 0){ if(expr_id1 >= 0){ expr1 = expressions[expr_id1]; } if(expr_id2 >= 0){ expr2 = expressions[expr_id2]; } expr->value = expr1->value * expr2->value; PLUSExpressionToList(expr); } if(expr_id1 == -1 && expr_id2 == -1){ //expressions have num token expr->value = expr1->value * expr2->value; PLUSExpressionToList(expr); } else{ error = 1; char * src = "ERROR at line %d: Assigment to number is invalid\n"; char * dest = (char *)malloc(strlen(src) + expr->lineNum + 10); sprintf(dest, src, expr->lineNum); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } } else{ error = 1; if(expr_id1 == -2) { char * src = "ERROR at line %d: %s is undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr1->identifier) + expr1->lineNum + 10); sprintf(dest, src, expr1->lineNum, expr1->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } if(expr_id2 == -2) { char * src = "ERROR at line %d: %s is undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr2->identifier) + expr2->lineNum + 10); sprintf(dest, src, expr2->lineNum, expr2->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } return NULL; } } ExprNode * divExpr(ExprNode * expr1, ExprNode * expr2){ int expr_id1 = checkIdentifier(expr1); int expr_id2 = checkIdentifier(expr2); //int result_id = checkIdentifier(expr); ExprNode * expr = (ExprNode *)malloc(sizeof(ExprNode)); expr->identifier = NULL; expr->lineNum = expr2->lineNum; //printf("Result id %d\n", result_id); //int result_id = checkIdentifier(expr); if(expr_id1 >= -1 && expr_id2 >= -1 ){ if(expr_id1 >= 0 || expr_id2 >= 0){ if(expr_id1 >= 0){ expr1 = expressions[expr_id1]; } if(expr_id2 >= 0){ expr2 = expressions[expr_id2]; } expr->value = expr1->value / expr2->value; PLUSExpressionToList(expr); } if(expr_id1 == -1 && expr_id2 == -1){ //expressions have num token expr->value = expr1->value / expr2->value; PLUSExpressionToList(expr); } else{ error = 1; char * src = "ERROR at line %d: Assigment to number is invalid\n"; char * dest = (char *)malloc(strlen(src) + expr->lineNum + 10); sprintf(dest, src, expr->lineNum); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } } else{ error = 1; if(expr_id1 == -2) { char * src = "ERROR at line %d: %s is undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr1->identifier) + expr1->lineNum + 10); sprintf(dest, src, expr1->lineNum, expr1->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } if(expr_id2 == -2) { char * src = "ERROR at line %d: %s is undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr2->identifier) + expr2->lineNum + 10); sprintf(dest, src, expr2->lineNum, expr2->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } return NULL; } } ExprNode * subExpr(ExprNode * expr1, ExprNode * expr2){ int expr_id1 = checkIdentifier(expr1); int expr_id2 = checkIdentifier(expr2); //int result_id = checkIdentifier(expr); ExprNode * expr = (ExprNode *)malloc(sizeof(ExprNode)); expr->identifier = NULL; expr->lineNum = expr2->lineNum; //printf("Result id %d\n", result_id); //int result_id = checkIdentifier(expr); if(expr_id1 >= -1 || expr_id2 >= -1 ){ if(expr_id1 >= 0 || expr_id2 >= 0){ if(expr_id1 >= 0){ expr1 = expressions[expr_id1]; } if(expr_id2 >= 0){ expr2 = expressions[expr_id2]; } expr->value = expr1->value - expr2->value; PLUSExpressionToList(expr); } if(expr_id1 == -1 && expr_id2 == -1){ //expressions have num token expr->value = expr1->value - expr2->value; PLUSExpressionToList(expr); } else{ error = 1; char * src = "ERROR at line %d: Assigment to number is invalid\n"; char * dest = (char *)malloc(strlen(src) + expr->lineNum + 10); sprintf(dest, src, expr->lineNum); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } } else{ error = 1; if(expr_id1 == -2) { char * src = "ERROR at line %d: %s is undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr1->identifier) + expr1->lineNum + 10); sprintf(dest, src, expr1->lineNum, expr1->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } if(expr_id2 == -2) { char * src = "ERROR at line %d: %s is undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr2->identifier) + expr2->lineNum + 10); sprintf(dest, src, expr2->lineNum, expr2->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } return NULL; } } int checkIdentifier(ExprNode * expr){ /* RETURNS: -1 -> Number -2 -> not found i >= 0 -> index of identifier */ if(expr->identifier == NULL){ return -1; } int i = 0; for(;i<exprIndex;i++){ //printf("Expr 1 %s - Expr 2 %s\n", expr->identifier, expressions[i]->identifier); if(strcmp(expr->identifier, expressions[i]->identifier) == 0 ){ //printf("Expr index %d identifier %s\n", i, expressions[i]->identifier); //if they are equal return its occurence return i; } } return -2; } int PLUSExpressionToList(ExprNode * newExpr){ /* PLUS expression to expressions list */ if(exprIndex < expressionsSize){ expressions[exprIndex] = newExpr; exprIndex += 1; } else{ expressionsSize = expressionsSize + expressionsSize; expressions = realloc(expressions, expressionsSize); expressions[exprIndex] = newExpr; exprIndex += 1; } } //["Set", "x", "3"] : tSET tIDENT expr void assign(ExprNode * expr1, ExprNode * expr2){ int expr_id1 = checkIdentifier(expr1); int expr_id2 = checkIdentifier(expr2); if(expr_id2 >= -1 && expr_id1 >= -1){ if(expr_id1 >= 0 || expr_id2 >= 0){ expr2 = expressions[expr_id2]; expr1 = expressions[expr_id1]; expr1->value = expr2->value; } else if(expr_1 >= 0 || expr_id2 = -1){ expr1 = expressions[expr_id1]; expr_1->value = expr2 } else{ error = 1; char * src = "Type missmatch on %d\n", expr2->lineNum ; char * dest = (char *)malloc(strlen(src) + expr2->lineNum + 10); sprintf(dest, src, expr2->lineNum); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } } else{ error = 1; char * src = "Never initialized before undefined\n"; char * dest = (char *)malloc(strlen(src) + strlen(expr2->identifier) + expr2->lineNum + 10); sprintf(dest, src, expr2->lineNum, expr2->identifier); if(errorIndex < errorSize){ errors[errorIndex] = dest; errorIndex += 1; } else{ errorSize = errorSize + errorSize; errors = realloc(errors, errorSize); errors[errorIndex] = dest; errorIndex += 1; } } } int main () { expressions = (ExprNode**)malloc(expressionsSize * sizeof(ExprNode*)); errors = (char**)malloc(errorSize * sizeof(char*)); if (yyparse()) { // parse error printf("ERROR\n"); return 1; } else { if(error == 0){ int i = 0; for(;i<exprIndex;i++){ printf("Expression first defined at line %d with identifier %s with value %d\n", expressions[i]->lineNum, expressions[i]->identifier, expressions[i]->value ); } // successful parsing } else{ int i = 0; for(;i<errorIndex;i++){ printf(errors[i]); } } //printf("OK\n"); return 0; } }