Example #1
0
tChyba TERM2() {
	int analyza;
	TItem *pt2;
	TItem *pt;
	bool nasel = false;
	//TERM2->( DRUH TERM2
	if(token.stav == s_leva_zavorka) {
			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}
		if(token.stav == s_cele_cislo || token.stav == s_desetinne_cislo || token.stav == s_logicka_hodnota || token.stav == s_string || token.stav == s_identifikator) {
			analyza = DRUH();
			if(analyza != S_BEZ_CHYB) {
				return analyza;
			}//pokud nejsme v definici funkce, pridej do nove vznikleho ramce zadany argument
			if(byla_funkce == false) {
				int ret = addArgument(token.data);
				if( ret != S_BEZ_CHYB ){
					return ret;
				}
			}
			//vyhledani volane funkce
			pt = htSearch(ptrhtGlobal, porovnani);
			//vyhledani funkce, ve ktere se vola funkce
			pt2 = htSearch(ptrhtGlobal, funkce); 
			if(token.stav == s_identifikator) {
					//pokud to bylo id
				if(pt != NULL) {
					for (int i = 0; i < pt2->data->param.numParam; ++i){			//prochazime pole parametru
						if(!strcmp(token.data, pt2->data->param.param[i])) {		//pokud najdeme parametr tak nastavime na true
							if(pt->data->param.typeParam[i] != pt2->data->param.typeParam[i]) { //kontrolujeme jestli datove typy parametru jsou stejne
								return S_SEMANTICKA_CHYBA_TYPOVA;
							}

							nasel = true;
							break;
						}				
					}

					if(nasel != true) { //POKUD NENI PARAMETR PROJDEME 
						pt2 = searchFrames(token.data, ptrhtLocal, ptrhtGlobal); 
						if(pt2 != NULL) {
							//kontrola datovych typu parametru funkce a argumentu		
							if(pt->data->param.typeParam[pocitadlo] != pt2->type) {
								return S_SEMANTICKA_CHYBA_TYPOVA;
							}		
						}	
						else {
							return S_SEMANTICKA_CHYBA_NEDEF;
						}
					}		
				}	
				else {
					return S_SEMANTICKA_CHYBA_NEDEF;
				}			

				nasel = false;
			}
			else {
				if(pt != NULL) {
					if(token.stav != pt->data->param.typeParam[pocitadlo]) {
						return S_SEMANTICKA_CHYBA_TYPOVA;
					}
				}
				else {
					return S_SEMANTICKA_CHYBA_NEDEF;
				}	
			}

			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}
			pocitadlo++;
			return TERM2();
		}	
	}
	//TERM2->, DRUH TERM2
	else if(token.stav == s_carka) {
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}
		//pridani argumentu do vznikle tabulky
		if(byla_funkce == false) {
			int ret = addArgument(token.data);
			if( ret != S_BEZ_CHYB ){
				return ret;
			}
		}
		if(token.stav == s_cele_cislo || token.stav == s_desetinne_cislo || token.stav == s_logicka_hodnota || token.stav == s_string || token.stav == s_identifikator) {
			analyza = DRUH();
			if(analyza != S_BEZ_CHYB) {
				return analyza;
			}
			//vyhledani volane funkce
			pt = htSearch(ptrhtGlobal, porovnani);
			//vyhledani funkce, ve ktere se vola funkce
			pt2 = htSearch(ptrhtGlobal, funkce); 
			if(token.stav == s_identifikator) {
				if(pt != NULL) {	
					for (int i = 0; i < pt2->data->param.numParam; ++i){
						if(!strcmp(token.data, pt2->data->param.param[i])) {
							//kontrola zda souhlasi datove typy parametru 2 funkci
							if(pt->data->param.typeParam[i] != pt2->data->param.typeParam[i]) {
								return S_SEMANTICKA_CHYBA_TYPOVA;
							}

							nasel = true;
							break;
						}				
					}
					//pokud to neni parametr, kontrola jestli je id v tabulkach
					if(nasel != true) {
						pt2 = searchFrames(token.data, ptrhtLocal, ptrhtGlobal);
						if(pt2 != NULL) {			
							if(pt->data->param.typeParam[pocitadlo] != pt2->type) {
								return S_SEMANTICKA_CHYBA_TYPOVA;
							}	
						}
						else {
							return S_SEMANTICKA_CHYBA_NEDEF;
						}
					}		
				}	
				else {
					return S_SEMANTICKA_CHYBA_NEDEF;
				}			
				
				nasel = false;
			}
			else {//kontrola datovych typu
				if(token.stav != pt->data->param.typeParam[pocitadlo]) {
					return S_SEMANTICKA_CHYBA_TYPOVA;
				}
			}	

		}

		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}

		pocitadlo++;
		return TERM2();
		
	}
	else if(token.stav == s_prava_zavorka) {
		pt = htSearch(ptrhtGlobal, porovnani);			
		//zjistime, zda pocet zadanych parametru odpovida poctu parametru pri deklaraci funkce
		if(pocitadlo != pt->data->param.numParam) {
			return S_SEMANTICKA_CHYBA_TYPOVA;
		}
		
		if(byla_funkce == true) {//pokud jsme v definici funkce
			//generovani instrukce fake call
			generateInstruction(OC_COLL, htSearch(ptrhtGlobal, porovnani ), NULL, NULL );
			generateInstruction(OC_NEPRIRAZENI, NULL, NULL, NULL );
		}
		else{
			//vygenerovani instrukci InsertFirst
			for (int i = 0; i < MAX_HTSIZE; ++i){
				if( (*ptrhtLocal)[i] ){
					if( (*ptrhtLocal)[i]->druh == ID_FUNCTION  ){
						generateCopyInstr(OC_CPY, (*ptrhtLocal)[i], NULL, NULL );
					}
				}
			}
			//predchozi list instrukci, protoze se volal push
			listIntrukci = &(ptrStack->top->lower->field);
			//htPrintTable(ptrhtGlobal);
			//param CALL, Funkce v GLOBALCE, NULL, NAVRATOVKA
			generateInstruction(OC_CALL, htSearch(ptrhtGlobal, porovnani ), NULL, htSearch( ptrhtLocal, porovnani ) );
			//PRIRAZ, NAVRATOVKA, NULL, IDCKO
			generateInstruction(OC_PRIRAZENI, htSearch( ptrhtLocal, porovnani ), NULL, searchFrames( id, ptrhtLastLocal, ptrhtGlobal ) );
			//nastaveni spravneho listu instrukci
			listIntrukci = &(ptrStack->top->field);
			//instrukce return na konci volane fce
			generateInstruction(OC_RET, NULL, NULL, NULL );
		}
		//globalni promenna -> musime nulovat
		pocitadlo = 0;								 
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}
		return S_BEZ_CHYB;
	}
	return S_SYNTAKTICKA_CHYBA;
}
Example #2
0
tChyba TERM() {
	int analyza;
	TItem *pt, *pt2;
	
	//TERM->( DRUH TERM
	if(token.stav == s_leva_zavorka) {
			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}
		if(token.stav == s_cele_cislo || token.stav == s_desetinne_cislo || token.stav == s_logicka_hodnota || token.stav == s_string || token.stav == s_identifikator) {
			analyza = DRUH();
			if(analyza != S_BEZ_CHYB) {
				return analyza;
			}
			
			if(token.stav == s_identifikator) {
				//pokud jsme v definici funkce
				if(byla_funkce == true) {
					pt = searchFrames(funkce, ptrhtLocal, ptrhtGlobal);
					if(pt != NULL) {
						//kontrolujeme, zda zadany argument je parametr funkce
						for (int i = 0; i < pt->data->param.numParam; ++i){	
							if(!strcmp(token.data, pt->data->param.param[i])){
								
								break;
							}
						}
					}
				}		
				//zjistime, zda id je v nejake tabulce
				pt2 = searchFrames(token.data, ptrhtLocal, ptrhtGlobal);
				if(pt2 == NULL) {
					return S_SEMANTICKA_CHYBA_NEDEF;
				}
				//generovani instrukce write
				generateInstruction( OC_WRITE, pt2 , NULL, NULL );
						
								
			}
			else{//pokud neni id, ale primo hodnota
				TItem *str = (TItem*)malloc(sizeof(TItem));
				str->druh = PRINTSTR;
				str->type = TYPESTR;
				str->init = true;
				str->data = (TData*)malloc(sizeof(TData));
				str->data->str = allocString(token.data);
				//jako nahore
				generateInstruction( OC_WRITE, str , NULL, NULL );
			}

			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}
			return TERM();
		}	
	}
	//TERM->, DRUH TERM
	else if(token.stav == s_carka) {
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}

		if(token.stav == s_cele_cislo || token.stav == s_desetinne_cislo || token.stav == s_logicka_hodnota || token.stav == s_string || token.stav == s_identifikator) {
			analyza = DRUH();
			if(analyza != S_BEZ_CHYB) {
				return analyza;
			}

			if(token.stav == s_identifikator) {
				//pokud jsme v definici funkce hledej i na parametry, jinak je ve "funkce" nic.
				if(byla_funkce == true) {
					pt = searchFrames(funkce, ptrhtLocal, ptrhtGlobal);
					if(pt != NULL) {
						for (int i = 0; i < pt->data->param.numParam; ++i){	
							if(!strcmp(token.data, pt->data->param.param[i])){
								
								break;
							}
						}
					}
				}		

				pt2 = searchFrames(token.data, ptrhtLocal, ptrhtGlobal);
				if(pt2 == NULL) {
					return S_SEMANTICKA_CHYBA_NEDEF;
				}//generovani instrukce write
				generateInstruction( OC_WRITE, pt2 , NULL, NULL );
			}
			else{//pokud je argument hodnota
				TItem *str = (TItem*)malloc(sizeof(TItem));
				str->druh = PRINTSTR;
				str->init = true;
				str->type = TYPESTR;
				str->data = (TData*)malloc(sizeof(TData));
				str->data->str = allocString(token.data);
				generateInstruction( OC_WRITE, str , NULL, NULL );
			}

			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}
			return TERM();
		}
	}
	else if(token.stav == s_prava_zavorka) {
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}
		return S_BEZ_CHYB;
	}
	return S_SYNTAKTICKA_CHYBA;
}
Example #3
0
File: expr.c Project: Dasio/IFJ
// 3, 4, 6, 8 .. tokens
static inline void reduce_handle_function(THandle handle)
{
	int num_of_commas = 0;
	ExprToken *temp = handle.first;
	if ((++temp)->token->type != TT_leftBrace)
	{
		setError(ERR_Reduction);
		return;
	}
	temp++;

	Symbol *id = SymbolFind(mainContext, handle.first->token->str.data);
	Context *context = id->funCont;
	return_value_data_type = (DataType) context->returnType;

	for (int32_t i = 0; i < context->argCount; i++) // check arguments
	{
		if (temp->E.data_type != context->arg[i]->type)
		{
			setError(ERR_TypeCompatibilityArg);
			return;
		}
		if (i != context->argCount - 1 && (++temp)->token->type != TT_comma)
		{
			setError(ERR_ArgCount);
			return;
		}
		temp++;
	}
	// check the end of handle
	if ((temp)->token->type != TT_rightBrace || temp != handle.last)
	{
		setError(ERR_Reduction);
		return;
	}

	// reserve place for return value
	b.var_type = CONST; // for pushing initialized flag
	b.initialized = false;
	a.offset = MY_OFFSET++;
	generateInstruction(PUSH, &a, &b, &c); // b = pushed operand

	if (id->index >= 0)	 // normal functions
	{
		for (int32_t i = 0; i < context->argCount; i++) // push arguments in reversed order
		{
			temp--;

			b = temp->E;
			b.initialized = true;
			a.offset = MY_OFFSET++;
			generateInstruction(PUSH, &a, &b, &c); // b = pushed operand, a = local dst

			temp--;
		}
	}
	else // built-in functions
	{
		for (int32_t i = 0; i < context->argCount; i++) // push arguments in reversed order
		{
			temp--;

			b = temp->E;
			b.initialized = true;
			a.offset = MY_OFFSET++;
			generateInstruction(PUSHX, &a, &b, &c); // b = pushed operand, a = local dst

			temp--;
		}
	}

	if (id->stateFunc == FS_Declared)
		int64_tVectorAppend(id->adressVector, tape->used);

	a.offset = id->index;
	c.offset = MY_OFFSET - 1;

	// generate CALL instruction
	switch (a.offset)
	{
		case -1:
			generateInstruction(CALL_LENGTH, &a, &b, &c);
			break;
		case -2:
			generateInstruction(CALL_COPY, &a, &b, &c);
			break;
		case -3:
			generateInstruction(CALL_FIND, &a, &b, &c);
			break;
		case -4:
			generateInstruction(CALL_SORT, &a, &b, &c);
			break;
		default:
			b.int_ = context->locCount;
			generateInstruction(CALL, &a, &b, &c);
			break;
	}

	// reducing tokenvector
	MY_OFFSET -= context->argCount;
	handle.first->handle_start = false;
	handle.first->type = NONTERM;
	handle.first->E.data_type = return_value_data_type;
	handle.first->E.var_type = LOCAL;
	handle.first->E.offset = MY_OFFSET - 1;
	if (context->argCount > 1)
		num_of_commas = context->argCount - 1;
	ExprTokenVectorPopMore(handle.expr_vector, context->argCount + 2 + num_of_commas);
}
Example #4
0
tChyba ACT_LIST() {
	int analyza;
	int dtype2=0;
	TItem *pt;
	//ACT_LIST->end	
	if(!strcmp(token.data, "end") && token.stav == s_klicove) {
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}
		return S_BEZ_CHYB;
	}
	//ACT_LIST->begin ACT_LIST 
	else if(!strcmp(token.data, "begin") && token.stav == s_klicove) {
		
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}
		return ACT_LIST();
	}
	//ACT_LIST->id LEXEM ROZHODNI UKONCOVACI
	else if(token.stav == s_identifikator) {

		if((id = malloc(strlen(token.data)+1)) == NULL)	{
				return S_INTERNI_CHYBA;
			}
		//kopirovani z token.data do globalni		
		strcpy(id, token.data);	
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}

		analyza = LEXEM();

		if(analyza != S_BEZ_CHYB) {
			return analyza;
		}
		
		//pokud se jedna o deklaraci id, dojde k ulozeni jeho datoveho typu
		if(!strcmp(token.data, "integer")) {
			dtype2 = TYPEINT;
		}
		else if(!strcmp(token.data, "string")) {			
			dtype2 = TYPESTR;
		}
		else if(!strcmp(token.data, "real")) {
			dtype2 = TYPEDOUBLE;
		}
		else if(!strcmp(token.data, "boolean")) {
			dtype2 = TYPEBOOL;
		}
		//pokud je prirazeni zkontroluj ze je v nejake tabulce
		if(prirovnani == true) {
			pt = searchFrames(id, ptrhtGlobal, ptrhtLocal);
			if(pt != NULL) {
				prirovnani = false;
			}
			else {
				return S_SEMANTICKA_CHYBA_NEDEF;
			}
		}

		analyza = ROZHODNI();
		if(analyza != S_BEZ_CHYB) {
			return analyza;
		}
		//pokud byla deklarace, ulozime id do lokalniho ramce
		if(dtype2 != 0) {									
			htDeclInsert(ptrhtLocal,id, dtype2, ID_LOCAL);			
			free(id);
		}
		
		analyza = UKONCOVACI();
		if(analyza != S_BEZ_CHYB) {
			return analyza;
		}
		return S_BEZ_CHYB;
	}
	else if(!strcmp(token.data, "var") && token.stav == s_klicove) {
		//ACT_LIST->var id : DTYPE ; ACT_LIST

		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}
		if(token.stav == s_identifikator) {
			if((id = malloc(strlen(token.data)+1)) == NULL)	{
				return S_INTERNI_CHYBA;
			}
			//nesmi se id jmenovat stejne jak tyto funkce
			if(!strcmp(token.data, "length") || !strcmp(token.data, "copy")) {			
				return S_SEMANTICKA_CHYBA_NEDEF;
			}
			//pokud j*z nazev existuje -> chyba
			pt = searchFrames(token.data, ptrhtLocal, ptrhtGlobal);				
			if(pt != NULL) {
				return S_SEMANTICKA_CHYBA_NEDEF;
			}

			strcpy(id, token.data);		
			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}

			else if(token.stav == s_dvojtecka) {
				token = getNextToken();
				if(token.stav == s_lex_error) {
					return S_LEXIKALNI_CHYBA;
				}

				analyza = DTYPE();
				if(analyza != S_BEZ_CHYB) {
					return analyza;
				}
				
				if(!strcmp(token.data, "integer")) {
					dtype = TYPEINT;
				}
				else if(!strcmp(token.data, "string")) {
					dtype = TYPESTR;
				}
				else if(!strcmp(token.data, "real")) {
					dtype = TYPEDOUBLE;
				}
				else if(!strcmp(token.data, "boolean")) {
					dtype = TYPEBOOL;
				}
			
				//vlozeni id do lokalniho ramce
				htDeclInsert(ptrhtLocal,id, dtype, ID_LOCAL);		
				free(id);
				
				
				token = getNextToken();
				if(token.stav == s_lex_error) {
					return S_LEXIKALNI_CHYBA;
				}	

				else if(token.stav == s_strednik) {
					token = getNextToken();
					if(token.stav == s_lex_error) {
						return S_LEXIKALNI_CHYBA;
					}
					return ACT_LIST();
				}
			}
		}
		return S_SYNTAKTICKA_CHYBA;
	}
	//ACT_LIST->if EXPR then CYKLUS else CYKLUS UKONCOVACI
	else if(!strcmp(token.data, "if") && token.stav == s_klicove) {
		
		//inkrementace labelu -> vime kolik je vnorenych ifu v sobe
		lab++;
		//vlozeni hodnoty lab do TItem data
		TItem *tmp = (TItem*)malloc(sizeof(TItem));
		tmp->type = TYPEINT;
		tmp->init = true;
		tmp->data = (TData*)malloc(sizeof(TData));
		tmp->data->intNumber = lab;

		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}
		//po if nasleduje vyraz, zavolame precedencni na vyhodnoceni	
		analyza = precedencniSA();			
		if(analyza != S_BEZ_CHYB) {
			return analyza;
		}
		//generovani skoku, tmp1 je logicka hodnota, tmp3 je lab
		generateInstruction(OC_GOTO, searchFrames(neterminal.polozkaTS.key, ptrhtLocal, ptrhtGlobal), NULL, tmp );
		if(!strcmp(token.data, "then") && token.stav == s_klicove) {
			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}
		
			analyza = CYKLUS();
			if(analyza != S_BEZ_CHYB) {
				return analyza;
			}
			//generovani skoku za else
			generateInstruction(OC_GOTOAFTER, searchFrames(neterminal.polozkaTS.key, ptrhtLocal, ptrhtGlobal), NULL, tmp );
			if(!strcmp(token.data, "else") && token.stav == s_klicove) {
				//generovani navesti skok do else
				generateInstruction(OC_ELSE, NULL, NULL, tmp);
				token = getNextToken();
				if(token.stav == s_lex_error) {
					return S_LEXIKALNI_CHYBA;
				}
				
				analyza = CYKLUS();
				if(analyza != S_BEZ_CHYB) {
					return analyza;
				}
				//generovani navesti skok za else
				generateInstruction(OC_AFTER_ELSE, NULL, NULL, tmp);
				lab--;
				return UKONCOVACI();
			}
			return S_SYNTAKTICKA_CHYBA;
			
		}
		return S_SYNTAKTICKA_CHYBA;
	}
	//ACT_LIST->while EXPR do CYKLUS  UKONCOVACI
	else if(!strcmp(token.data, "while") && token.stav == s_klicove) {
		
		//opet na zjisteni jak moc jsme zanoreni
		lab_while++;
		TItem *tmp = (TItem*)malloc(sizeof(TItem));
		tmp->type = TYPEINT;
		tmp->init = true;
		tmp->data = (TData*)malloc(sizeof(TData));
		tmp->data->intNumber = lab_while;
		
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}

		//generovani navesti skok pred vyhodnoceni podminky
		generateInstruction(OC_WHILE_PRED, NULL, NULL, tmp);
		
		analyza = precedencniSA();
		if(analyza != S_BEZ_CHYB) {
			return analyza;
		}
		//generovani skoku, tmp1 je logicka hodnota, tmp3 je lab
		generateInstruction(OC_GOTO_WHILE, searchFrames(neterminal.polozkaTS.key, ptrhtLocal, ptrhtGlobal), NULL, tmp );
		if(!strcmp(token.data, "do") && token.stav == s_klicove) {
			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}

			analyza = CYKLUS();
			if(analyza != S_BEZ_CHYB) {
				return analyza;
			}
			//generovani skoku zpet na zacatek 
			generateInstruction(OC_GOTO_WHILE, searchFrames(neterminal.polozkaTS.key, ptrhtLocal, ptrhtGlobal), NULL, tmp );
			//navesti pro skonceni cyklu
			generateInstruction(OC_WHILE_AFTER, NULL, NULL, tmp);
			lab_while--;
			return UKONCOVACI();
		}
		return S_SYNTAKTICKA_CHYBA;
	}
	//ACT_LIST->readln ( id ) UKONCOVACI
	else if(!strcmp(token.data, "readln") && token.stav == s_klicove) {
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}

		if(token.stav == s_leva_zavorka) {
			token = getNextToken();
			if(token.stav == s_lex_error) {
				return S_LEXIKALNI_CHYBA;
			}

			else if(token.stav == s_identifikator) {
				//pokud zadany parametr nebyl deklarovan -> chyba
				pt = searchFrames(token.data, ptrhtLocal, ptrhtGlobal);				
				if(pt == NULL) {
					return S_SEMANTICKA_CHYBA_NEDEF;
				}
				//pokud je datovy typ parametru boolean -> chyba
				if(pt->type == TYPEBOOL) {
					return S_SEMANTICKA_CHYBA_TYPOVA;
				}
				//generovani instrukce read, v token.data je id
				generateInstruction(OC_READ, NULL, NULL, searchFrames(token.data,ptrhtLocal,ptrhtGlobal));		
				token = getNextToken();
				if(token.stav == s_lex_error) {
					return S_LEXIKALNI_CHYBA;
				}

				else if(token.stav == s_prava_zavorka) {
					token = getNextToken();
					if(token.stav == s_lex_error) {
						return S_LEXIKALNI_CHYBA;
					}

					analyza = UKONCOVACI();
					if(analyza != S_BEZ_CHYB) {
						return analyza;
					}
					return S_BEZ_CHYB;
					
				}
			}
			else {
				return S_SEMANTICKA_CHYBA_TYPOVA;
			}
		}
		return S_SYNTAKTICKA_CHYBA;
	}
	//ACT_LIST->write TERM UKONCOVACI
	else if(!strcmp(token.data, "write") && token.stav == s_klicove) {
		token = getNextToken();
		if(token.stav == s_lex_error) {
			return S_LEXIKALNI_CHYBA;
		}
		
		
			analyza = TERM();
			if(analyza != S_BEZ_CHYB) {
				return analyza;
			}
			
			analyza = UKONCOVACI();
			if(analyza != S_BEZ_CHYB) {
				return analyza;
			}
			
			return S_BEZ_CHYB;
		
	}
	return S_SYNTAKTICKA_CHYBA;
}
Example #5
0
File: expr.c Project: Dasio/IFJ
DataType expr()
{
	int action;
	instr_counter = 0;
	bool end_of_eval = true;
	return_value_data_type = EXPR_ERROR;
	assert(activeContext);
	if (activeContext == mainContext)
		MY_OFFSET = activeContext->locCount + 1;
	else
		MY_OFFSET = activeContext->locCount + 2;

	token++;

	if(token->type != TT_leftBrace && token->type != TT_not && token->type != TT_minus
		&& !(token->type >= TT_identifier && token->type <= TT_bool))
	{
		setError(ERR_SyntaxExpr);
		return EXPR_ERROR;
	}

	ExprTokenVector *expr_token_vector = ExprTokenVectorInit(32);

	assert(tokenVector);
	convert_to_ExprToken(TokenVectorLast(tokenVector), expr_token_vector); // add $ to expr. stack
	ExprTokenVectorAppend(expr_token_vector, temp_expr_token); // first token, (empty = $)
	// [$, , , , , ]

	while (end_of_eval)
	{
		convert_to_ExprToken(token, expr_token_vector);
		if(getError())
		{
			ExprTokenVectorFree(expr_token_vector);
			return EXPR_ERROR;
		}

AFTER_REDUCE:
		action = precedence(expr_token_vector);

		/* vypisy */
		//static const char *actions[] = {"shift", "reduce", "handle", "error"};
		//ExprTokenVectorPrint(expr_token_vector);
		//fprintf(stderr, " %s\n", actions[action]);

		switch(action)
		{
			case ERROR:
				if (top_most_term->token->type == TT_empty &&
					token_to_index(temp_expr_token.token) == TT_empty &&
					expr_token_vector->used != 3)
				{
					end_of_eval = false;
					break;
				}
				setError(ERR_PrecedenceTable);
				ExprTokenVectorFree(expr_token_vector);
				return EXPR_ERROR;
			case SHIFT:
				ExprTokenVectorAppend(expr_token_vector, temp_expr_token);
				if (top_most_term != ExprTokenVectorLast(expr_token_vector))
					top_most_term[1].handle_start = true;
				break;
			case HANDLE:
				ExprTokenVectorAppend(expr_token_vector, temp_expr_token);
				break;
			case REDUCE:
				reduce(expr_token_vector);
				if(getError())
				{
					ExprTokenVectorFree(expr_token_vector);
					return EXPR_ERROR;
				}
				goto AFTER_REDUCE;
				break;
		}
		if (token_to_index(token) != TT_empty)
			token++;
	}


	/*for (int i = TT_unaryMinus; i <= TT_inequality; i++)
	{
		printf("%d\n", i);
		print_type_table(i);
	}*/

	Instruction *last = InstructionVectorLast(tape);
	if (instr_counter == 0)
	{
		b = (++top_most_term)->E;
		b.initialized = true;
		a.offset = MY_OFFSET++;
		//fprintf(stderr,"EXPR_PUSH a.offset = %ld b.var_type = %d b.offset= %ld b.data_type= %d\n",a.offset,b.var_type,b.offset,b.data_type);
		generateInstruction(PUSH, &a, &b, &c); // b = pushed operand, a = local dst
	}
	else if (last->instr == Instr_CALL)
	{
		b.var_type = LOCAL;
		b.data_type = return_value_data_type;
		b.offset = MY_OFFSET - 1;
		a.offset = MY_OFFSET - 1;
		generateInstruction(PUSH, &a, &b, &c); // b = pushed operand, a = local dst
	}

	ExprTokenVectorFree(expr_token_vector);

	return return_value_data_type;
}