/* * Removal of elements from the symbol table should be * done with care. For, it should be assured that * there are no references to the definition at the * moment of removal. This situation can not easily * checked at runtime, without tremendous overhead. */ void deleteSymbol(Module scope, Symbol prg){ InstrPtr sig; int t; sig = getSignature(prg); #ifdef _DEBUG_MODULE_ fprintf(stderr,"#delete symbol %s.%s from %s\n", getModuleId(sig), getFunctionId(sig), prg->name); #endif if (getModuleId(sig) && getModuleId(sig)!= scope->name ){ /* move the definition to the proper place */ /* default scope is the last resort */ Module c= findModule(scope, getModuleId(sig)); if(c ) scope = c; } t = getSymbolIndex(getFunctionId(sig)); if (scope->space[t] == prg) { scope->space[t] = scope->space[t]->peer; freeSymbol(prg); } else { Symbol nxt = scope->space[t]; while (nxt->peer != NULL) { if (nxt->peer == prg) { nxt->peer = prg->peer; nxt->skip = prg->peer; freeSymbol(prg); return; } nxt = nxt->peer; } } }
static void reclaimSymbols(void) { Symbol* sym; for(sym=symlist;sym;) { Symbol* next = sym->next; freeSymbol(sym); sym = next; } }
void freeTable(){ Node* iNode = symbolTable->head; Node* tmp; while (iNode != 0){ freeSymbol((Symbol*)iNode->value); tmp = iNode; iNode = iNode->next; free(tmp); } free(symbolTable); }
void genOperation(FILE* yyout, Symbol* leftSide, Symbol* rightSide, char* op ) { int r0, r1; r0 = ((ExtraInfo*)(leftSide->info))->nRegister; r1 = ((ExtraInfo*)(rightSide->info))->nRegister; int isFloat_ = isFloat( leftSide ); if( !isFloat_ ){ if(r0 == 7){ r0 = assignRegisters(0); if (r0 == -1){ r0 = checkOverflow(yyout, r0, TYPE_INTEGER); } ((ExtraInfo*)(leftSide->info))->nRegister = r0; extraInfoPerRegister[r0] = ((ExtraInfo*)(leftSide->info)); fprintf(yyout, "\tR%d = I(R7);\t//Recovering value from stack\n\tR7 = R7 + 4;\n", r0); } if(r1 == 7){ r1 = assignRegisters(0); if (r1 == -1){ r1 = checkOverflow(yyout, r1, TYPE_INTEGER); } ((ExtraInfo*)(leftSide->info))->nRegister = r1; extraInfoPerRegister[r1] = ((ExtraInfo*)(rightSide->info)); fprintf(yyout, "\tR%d = I(R7);\t//Recovering value from stack\n\tR7 = R7 + 4;\n", r1); } fprintf(yyout, "\tR%d = R%d %s R%d;\n", r0, r0,op, r1); }else{ if(r0 == 77){ r0 = assignRegisters(1); if (r0 == -1){ r0 = checkOverflow(yyout, r0, TYPE_FLOAT); } ((ExtraInfo*)(leftSide->info))->nRegister = r0; extraInfoPerDoubleRegister[r0] = ((ExtraInfo*)(leftSide->info)); fprintf(yyout, "\tRR%d = F(R7);\t//Recovering value from stack\n\tR7 = R7 + 4;\n", r0); } if(r1 == 77){ r1 = assignRegisters(1); if (r1 == -1){ r1 = checkOverflow(yyout, r1, TYPE_FLOAT); } ((ExtraInfo*)(leftSide->info))->nRegister = r1; extraInfoPerDoubleRegister[r1] = ((ExtraInfo*)(rightSide->info)); fprintf(yyout, "\tRR%d = F(R7);\t//Recovering value from stack\n\tR7 = R7 + 4;\n", r1); } fprintf(yyout, "\tRR%d = RR%d %s RR%d;\n", r0, r0,op, r1); } freeRegister( r1, isFloat_ ); freeSymbol(rightSide); }
// Generate the code for a parameter pass. Arguments: // - iRegister - index of register with the argument's value. // - method - called method symbol. // - iArgument - argument index. void genArgumentPass( FILE* yyout, Symbol* argumentSymbol, Symbol* method, int iArgument ) { Symbol* argument = getMethodArgument( method, iArgument ); int iRegister = ((ExtraInfo*)(argumentSymbol->info))->nRegister; int address = ((Variable*)( argument->info ) )->address; int isFloat_ = isFloat( argumentSymbol ); cstr regStr = getRegStr( isFloat_ ); // Get parameter. fprintf( yyout,"\t%c(R7+%d) = %s%d;\t// %iº Argument\n", pointerType( argument ), address, regStr, iRegister, iArgument+1 ); freeRegister( iRegister, isFloat_ ); freeSymbol(argumentSymbol); }
void ht_entry_free(entry_t * e, int freeSymbols) { if(e == NULL) return; else { ht_entry_free(e->next, freeSymbols); } if (freeSymbols) { freeSymbol(e->value); } free(e->key); free(e); }
void makeEmpty(Table T) { if(T==NULL){ fprintf(stderr, "Table Error: calling makeEmpty() on NULL Table reference\n"); exit(EXIT_FAILURE); } if(T->count==0){ fprintf(stderr, "Table Error: calling makeEmpty() on empty Table\n"); exit(EXIT_FAILURE); } Symbol S; while(T->count>0){ S = T->top; T->top = T->top->next; freeSymbol(&S); T->count--; } T->top = NULL; }
// Generate code for a "#{<variable>}" pattern in string literals. Also return // an "interpolationMark" ("%I", "%F", "%U", "%E") so grammar can build the // string literal that will be past to the puts call. cstr genVariableInterpolation( FILE* yyout, Symbol* symbol ) { static char interpolationMarks[][3] = { "%I", "%F", "%U", "%E" }; // Get type and register of symbol. ExtraInfo* info = (ExtraInfo*)(symbol->info); int reg = info->nRegister; int type = getType( symbol ); int isFloat_ = isFloat( symbol ); // Generate code for passing the variable to puts. Also index the // interpolationMarks vector. int mark = 0; switch( type ){ case TYPE_INTEGER: fprintf( yyout, "\tR7 = R7-4;\t// Memory for puts argument\n" ); fprintf( yyout, "\tI(R7) = R%d;\t// Storing value of var integer for puts\n", reg ); mark = 0; break; case TYPE_FLOAT: fprintf( yyout, "\tR7 = R7-4;\t// Memory for puts argument\n" ); fprintf( yyout, "\tF(R7) = RR%d;\t// Storing value of var integer for puts\n", reg ); mark = 1; break; case TYPE_CHAR: fprintf( yyout, "\tR7 = R7-1;\t// Memory for puts argument\n" ); fprintf( yyout, "\tU(R7) = R%d;\t// Storing value of var integer for puts\n", reg ); mark = 2; break; default: // FIXME: Better idea about showing error? // FIXME: Outside this is not tested. mark = 3; break; } // Free resources and return the interpolation mark. // FIXME: Good idea free them here? freeRegister( reg, isFloat_ ); freeSymbol( symbol ); return interpolationMarks[mark]; }
SymbolInfo* genArrayContent( FILE* yyout, SymbolInfo* leftSide, Symbol* literalInfo, SymbolInfo* arrayInfo ) { Symbol* varSymbol = leftSide->varSymbol; int position = arrayInfo->info; int address = ((Variable*)(varSymbol->info))->address; int nRegister = ((ExtraInfo*)(literalInfo->info))->nRegister; int elementSize = ((Type*)(((Type*)(((Variable*)(varSymbol->info))->type->info))->arrayInfo->type->info))->size; int isFloat_ = isFloat(leftSide->varSymbol); cstr regStr = getRegStr( isFloat_ ); switch(varSymbol->symType) { case SYM_GLOBAL: fprintf(yyout,"\t%c(0x%x + %d) = %s%d; //Initializing %s array\n",pointerType(varSymbol), address, elementSize*position, regStr, nRegister, varSymbol->name); break; case SYM_VARIABLE: if(((Variable*)(varSymbol->info))->symSubtype == SYM_LOCAL){ fprintf(yyout,"\t%c(R6 + %d) = %s%d; //Initializing %s array\n",pointerType(varSymbol), elementSize*position - address, regStr, nRegister, varSymbol->name); }else{ fprintf(yyout,"\t%c(R6 - %d) = %s%d; //Initializing %s array\n",pointerType(varSymbol), elementSize*position + address, regStr, nRegister, varSymbol->name); } break; case SYM_CONSTANT: break; default: //Error printf("Error in array content\n"); break; } arrayInfo->info++; freeRegister( ((ExtraInfo*)(literalInfo->info))->nRegister, isFloat_ ); freeSymbol(literalInfo); return arrayInfo; }
Symbol* genAccessVariable(FILE* yyout,cstr name, int symType, SymbolInfo* atribute) { Symbol* variable = searchVariable(symType, name); int isFloat_ = isFloat( variable ); int reg; int height = returnVariableHeight( symType, name ); //When trying to access an array variable outside a block //we can use expression register so we do not have to assign a new one if( atribute->info == TYPE_ARRAY && !isFloat_ && height == 0 ){ reg = ((ExtraInfo*)(atribute->exprSymbol->info))->nRegister; }else{ reg = assignRegisters( isFloat_ ); } cstr regStr = getRegStr( isFloat_ ); int elementSize = 0; if (isFloat_ == 0) reg = checkOverflow(yyout, reg, TYPE_INTEGER); else reg = checkOverflow(yyout, reg, TYPE_FLOAT); Symbol* returnSymbol = createExtraInfoSymbol(reg, isFloat_); ExtraInfo* aux = (ExtraInfo*)(returnSymbol->info); aux->nRegister = reg; aux->variable = variable; if(atribute->info == SYM_CLASS_VARIABLE){ //varSymbol gets the Symbol of the variable aux->variable = getClassVar(aux->variable,atribute->name); } if( atribute->info == TYPE_ARRAY ){ elementSize = ((Type*)(((Type*)(((Variable*)(aux->variable->info))->type->info))->arrayInfo->type->info))->size; } if( symType == SYM_VARIABLE ) { int accessRegister = genFrameAccess( yyout, height, reg, isFloat_ ); if(((Variable*)(aux->variable->info))->symSubtype == SYM_LOCAL){ if( atribute->info == TYPE_ARRAY ){ int expReg = ((ExtraInfo*)(atribute->exprSymbol->info))->nRegister; fprintf(yyout, "\tR%d = R%d * %d; //Calculate array %s position\n",expReg, expReg, elementSize, aux->variable->name); fprintf(yyout, "\tR%d = R%d - %d; //Calculate local %s position\n",expReg, expReg, returnAddress(symType,aux->variable->name), aux->variable->name); fprintf(yyout,"\t%s%d = %c(R%d + R%d); //%s[expr] = expr\n",regStr, reg, pointerType(aux->variable), accessRegister, expReg, aux->variable->name); if( !(atribute->info == TYPE_ARRAY && !isFloat_ && height == 0) ){ freeRegister( expReg, 0 ); } freeSymbol(atribute->exprSymbol); }else{ fprintf(yyout,"\t%s%d = %c(R%d - %d); //Loading value of var %s\n",regStr, reg, pointerType(aux->variable), accessRegister, returnAddress(symType,aux->variable->name), aux->variable->name); } }else{ if( atribute->info == TYPE_ARRAY ){ int expReg = ((ExtraInfo*)(atribute->exprSymbol->info))->nRegister; fprintf(yyout, "\tR%d = R%d * %d; //Calculate array %s position\n",expReg, expReg, elementSize, aux->variable->name); fprintf(yyout, "\tR%d = R%d + %d; //Calculate local %s position\n",expReg, expReg, returnAddress(symType,aux->variable->name), aux->variable->name); fprintf(yyout,"\t%s%d = %c(R%d + R%d); //%s[expr] = expr\n",regStr, reg, pointerType(aux->variable), accessRegister, expReg, aux->variable->name); if( !(atribute->info == TYPE_ARRAY && !isFloat_ && height == 0) ){ freeRegister( expReg, 0 ); } freeSymbol(atribute->exprSymbol); }else{ fprintf(yyout,"\t%s%d = %c(R%d + %d); //Loading value of var %s\n",regStr,reg, pointerType(aux->variable), accessRegister, returnAddress(symType,aux->variable->name), aux->variable->name); } } if( accessRegister != 6 ){ freeRegister( accessRegister, 0 ); } }else{ if( symType == SYM_GLOBAL ) { if( atribute->info == TYPE_ARRAY ){ int expReg = ((ExtraInfo*)(atribute->exprSymbol->info))->nRegister; fprintf(yyout, "\tR%d = R%d * %d; //Calculate array %s position\n",expReg, expReg, elementSize, aux->variable->name); fprintf(yyout,"\t%s%d = %c(0x%x + R%d); //Loading value of var %s[expr]\n",regStr, reg, pointerType(aux->variable), returnAddress(symType,aux->variable->name), expReg, aux->variable->name); if( !(atribute->info == TYPE_ARRAY && !isFloat_ && height == 0) ){ freeRegister( expReg, 0 ); } freeSymbol(atribute->exprSymbol); }else{ fprintf(yyout,"\t%s%d = %c(0x%x); //Loading value of var %s\n", regStr, reg, pointerType(aux->variable), returnAddress(symType,aux->variable->name), aux->variable->name); } //FIXME Las constantes van aqui }else{ } } freeSymbolInfo(atribute); return returnSymbol; }
Symbol* genAssignement(FILE* yyout, SymbolInfo* leftSide, Symbol* rightSide, int insideIfLoop) { ExtraInfo* rightInfo = (ExtraInfo*)(rightSide->info); Variable* leftInfo = (Variable*)(leftSide->varSymbol->info); int i, arraySize, elementSize; if( rightInfo->assignmentType == TYPE_ARRAY || leftSide->info == TYPE_ARRAY ){ arraySize = ((Type*)(leftInfo->type->info))->arrayInfo->nElements; elementSize = ((Type*)(((Type*)(leftInfo->type->info))->arrayInfo->type->info))->size; } int isFloat_ = isFloat(leftSide->varSymbol); cstr regStr = getRegStr( isFloat_ ); int height = returnVariableHeight( leftSide->varSymbol->symType, leftSide->varSymbol->name ); //Left side is a global variable if (leftSide->varSymbol->symType == SYM_GLOBAL){ //Aquí no afecta el derramado porque la asignacion se hace directamente a memoria. //var = Array / Class if( rightInfo->assignmentType == LOAD_ADDRESS ){ //FIXME Aqui deberiamos cargar la direccion de la variable, para arrays y clases }else{ //Right side is Array.new if( rightInfo->assignmentType == TYPE_ARRAY ){ for( i = 0; i < arraySize; i++ ){ fprintf(yyout,"\t%c(0x%x + %d) = %s%d; //Initializing %s array",pointerType(leftSide->varSymbol), leftInfo->address, elementSize*i, regStr, rightInfo->nRegister, leftSide->varSymbol->name); } }else{ //Assignement $var[expression] = expression if( leftSide->info == TYPE_ARRAY ){ int reg = ((ExtraInfo*)(leftSide->exprSymbol->info))->nRegister; fprintf(yyout, "\tR%d = R%d * %d; //Calculate array %s position\n",reg, reg, elementSize, leftSide->varSymbol->name); fprintf(yyout,"\t%c(0x%x + R%d) = %s%d; //%s[expr] = expr\n",pointerType(leftSide->varSymbol), leftInfo->address, reg, regStr, rightInfo->nRegister, leftSide->varSymbol->name ); freeRegister( reg, 0 ); freeSymbol(leftSide->exprSymbol); //Assignement $var = expression }else{ fprintf(yyout,"\t%c(0x%x) = %s%d; //%s = expr\n",pointerType(leftSide->varSymbol), leftInfo->address, regStr, rightInfo->nRegister, leftSide->varSymbol->name, isFloat_); } } } //Left side not a global varialbe }else if (leftSide->varSymbol->symType == SYM_VARIABLE){ //Obtenemos la direccion con el desplazamiento y almacenamos if( rightInfo->assignmentType == LOAD_ADDRESS ){ //FIXME Aqui deberiamos cargar la direccion de la variable, para arrays y clases }else{ int accessRegister = genFrameAccess( yyout, height, -1, 1 ); //Left side is a local variable if(((Variable*)(leftSide->varSymbol->info))->symSubtype == SYM_LOCAL){ //Right side is Array.new or [e,e,..,e] if( rightInfo->assignmentType == TYPE_ARRAY ){ for( i = 0; i < arraySize; i++ ){ fprintf(yyout,"\t%c(R%d - %d) = %s%d; //Initializing %s array\n",pointerType(leftSide->varSymbol), accessRegister,leftInfo->address - elementSize*i, regStr, rightInfo->nRegister, leftSide->varSymbol->name); } }else{ //Assignement var[expression] = expression if( leftSide->info == TYPE_ARRAY ){ int reg = ((ExtraInfo*)(leftSide->exprSymbol->info))->nRegister; fprintf(yyout, "\tR%d = R%d * %d; //Calculate array %s position\n",reg, reg, elementSize, leftSide->varSymbol->name); fprintf(yyout, "\tR%d = R%d - %d; //Calculate local %s position\n",reg, reg, leftInfo->address, leftSide->varSymbol->name); fprintf(yyout,"\t%c(R%d + R%d) = %s%d; //%s[expr] = expr (2)\n",pointerType(leftSide->varSymbol), accessRegister, reg, regStr, rightInfo->nRegister, leftSide->varSymbol->name); freeRegister( reg, 0 ); freeSymbol(leftSide->exprSymbol); //Assignement var = expression }else{ fprintf(yyout,"\t%c(R%d - %d) = %s%d; //%s = expr\n",pointerType(leftSide->varSymbol), accessRegister, leftInfo->address, regStr, rightInfo->nRegister, leftSide->varSymbol->name); } } } //Left side is an argument variable else{ //Right side is Array.new or [e,e,..,e] if( rightInfo->assignmentType == TYPE_ARRAY ){ for( i = 0; i < arraySize; i++ ){ fprintf(yyout,"\t%c(R%d + %d) = %s%d; //Initializing %s array\n",pointerType(leftSide->varSymbol), accessRegister, leftInfo->address + elementSize*i, regStr, rightInfo->nRegister, leftSide->varSymbol->name); } }else{ //Assignement var[expression] = expression if( leftSide->info == TYPE_ARRAY ){ int reg = ((ExtraInfo*)(leftSide->exprSymbol->info))->nRegister; fprintf(yyout, "\tR%d = R%d * %d; //Calculate array %s position\n",reg, reg, elementSize, leftSide->varSymbol->name); fprintf(yyout, "\tR%d = R%d - %d; //Calculate local %s position\n",reg, reg, leftInfo->address, leftSide->varSymbol->name); fprintf(yyout,"\t%c(R%d - R%d) = %s%d; //%s[expr] = expr\n",pointerType(leftSide->varSymbol), accessRegister, reg, regStr, rightInfo->nRegister, leftSide->varSymbol->name); freeRegister( reg, 0 ); freeSymbol(leftSide->exprSymbol); //Assignement var = expression }else{ fprintf(yyout,"\t%c(R%d + %d) = %s%d; //%s = expr\n",pointerType(leftSide->varSymbol), accessRegister, leftInfo->address, regStr, rightInfo->nRegister, leftSide->varSymbol->name); } } } if( accessRegister != 6 ){ freeRegister( accessRegister, 0 ); } } } if(!insideIfLoop){ int reg = rightInfo->nRegister; Method* method = getCurrentScope(); if(method->returnType){ int size = method->argumentsSize; if(!isFloat(method->returnType) && !isFloat_){ fprintf(yyout,"\t%c(R6 + %d) = R%d; //Store return value\n", pointerType(method->returnType), size, reg); }else{ if(isFloat(method->returnType) && isFloat_){ fprintf(yyout,"\t%c(R6 + %d) = RR%d; //Store return value\n", pointerType(method->returnType), size, reg); } } } } freeRegister( rightInfo->nRegister, isFloat_ ); freeSymbolInfo(leftSide); return rightSide; }