/**
 * Function representing the <st_factor_ident> prods
 */
void RecursiveDescentParser::st_factor_ident(TableEntry* te) {
	if(errorCondition) return;
	if(token == TK_LEFT_PARENTHESES) 
	{
#if DEBUG_PARSER
		std::cout << "<st_factor_ident> --> (<o_list>);\n";
#endif
		Token leftParen = token;
		token = scanner->getToken();
		ParamList* pList = o_list();
		
		if(te) {
			if(te->getEntryType()!=TableEntry::FUNCTION) {
				std::stringstream errorMsg;
				errorMsg << "'" << te->getName() << "' is not a function";
				errorHandler(errorMsg.str(), leftParen);
			} else {
				// now makes sure the lists match
				FunctionEntry* fe = (FunctionEntry*)te;
				if(pList) matchParameters(fe, pList, leftParen);
				
				iCode.threeAddressCode(TAC_PARAM, pList);
				iCode.threeAddressCode( 
						symTab.getNextAddress(), // throw away temporary
						TAC_CALL, 
						fe->getLabel(), 
						fe->getParamCount()
					);
			}
		} else {
			std::stringstream errorMsg;
			errorMsg << "Undeclared function";
			errorHandler(errorMsg.str(), leftParen);
		}
		
		match(TK_RIGHT_PARENTHESES);
		match(TK_SEMICOLON);
	} 
	else if(token == TK_LEFT_BRACKET || 
			token == TK_ASSIGNMENT) 
	{
#if DEBUG_PARSER		
		std::cout << "<st_factor_ident> --> <var_prime>=<exp>;\n";
#endif
		VariableEntry* vEntry = (VariableEntry*)te;
		Token startToken = token;
		
		attr varAttr  = var_prime(vEntry);
		match(TK_ASSIGNMENT);
		attr expAttr = exp();
		
		if(expAttr.type != varAttr.type) {
			std::stringstream errorMsg;
			errorMsg << "Type mismatch variable '" << vEntry->getName() << "'";
			errorHandler(errorMsg.str(), startToken);
		}
		
		if(varAttr.attrib == VA_ARRAY) {
			std::stringstream errorMsg;
			errorMsg << "Assignment error, array '" << vEntry->getName() << "' must be indexed.";
			errorHandler( errorMsg.str(), startToken );
		}
		
		if(vEntry->getAttribute() == VA_ARRAY) {
			//                       array addr                           value to assign   index
			iCode.threeAddressCode(vEntry->getAttr(), TAC_ASSIGN_TO_ADDRESS_AT, expAttr, varAttr);
		} else {
			iCode.threeAddressCode(vEntry->getAttr(), TAC_ASSIGN, expAttr);
		}
		
		match(TK_SEMICOLON);
	} 
	else 
	{
		errorHandler();
	}
}
Exemple #2
0
/*--------------------------------------------------------------------------------------*\
 * UApm : process()                                                                     *
 *        The APM/2 main function, throws a ERROR_* in case of errors                   *
\*--------------------------------------------------------------------------------------*/
UApm                   &UApm::process(void)
{
    char               *pcOption=0;
    COUNTRYCODE         countrycode={ 0 };
    COUNTRYINFO         countryinfo={ 0 };
    ULONG               ulInfoLength=0;
    int                 iTemp=0;
    char               *pcTemp;
    UCountryTranslate   ucountrytranslate[]= { 
                                               {  01L, "Us" },
                                               {  02L, "Fr" },
                                               {  07L, "Ru" },
                                               {  31L, "Nl" },
                                               {  32L, "Be" },
                                               {  33L, "Fr" },
                                               {  34L, "Es" },
                                               {  39L, "It" },
                                               {  41L, "Gr" },
                                               {  44L, "Us" },
                                               {  45L, "Dk" },
                                               {  46L, "Se" },
                                               {  47L, "No" },
                                               {  49L, "Gr" },
                                               {  61L, "Us" },
                                               {  81L, "Jp" },
                                               {  99L, "Us" },
                                               { 358L, "Fi" },
                                             };
    FILESTATUS3         filestatus3;

                                        /* Query country settings, to try to load NLS
                                           message file even if no /Language commandline
                                           option has been specified */
    DosQueryCtryInfo(sizeof(countryinfo), &countrycode, &countryinfo, &ulInfoLength);
    for(iTemp=0; iTemp<(sizeof(ucountrytranslate)/sizeof(ucountrytranslate[0])); iTemp++)
        {
        if(countryinfo.country==ucountrytranslate[iTemp].ulCountry)
            {
            pcTemp=strrchr(acMessageFileNls, '.');
            if(strlen(acMessageFileNls) && (pcTemp!=0))
                {
                pcTemp-=2;              /* Skip "Us" backwards to append "Xx.msg" */
                strcpy(pcTemp, ucountrytranslate[iTemp].acCountry);
                strcat(pcTemp, ".msg");
                }
            break;
            }
        }
                                        /* First, try to find the NLS message file, which
                                           of course can override our assumptions */
    if((pcOption=checkCommandlineOption("Language", TRUE))!=0)
        {
        if(pcOption==(char *)0xFFFFFFFF)
            {
            displayMessage(MSG_LOGO);
            displayMessage(MSG_PARAMETERS_MISSING);
            throw((int)ERROR_PARAMETERS_MISSING);
            }
                                        /* If language was specified, use it */
        iStatusFlag|=FLAG_NLS_MESSAGES_REQUESTED;
        pcTemp=strrchr(acMessageFileNls, '.');
        if(strlen(acMessageFileNls) && (pcTemp!=0))
            {
            pcTemp-=2;                  /* Skip "Us" backwards to append "Xx.msg" */
            strcpy(pcTemp, pcOption);
            strcat(pcTemp, ".msg");
            }
        }
                                        /* Now that we might have a NLS message file that is
                                           not Us, verify that it exists */
    if(strcmp(acMessageFileNls, acMessageFileUs))
        {
        if(DosQueryPathInfo(acMessageFileNls, FIL_STANDARD, &filestatus3, sizeof(filestatus3))!=NO_ERROR)
            {
                                        /* The NLS message file specified does not exists, so use
                                           Us English one, but inform the user if he has requested
                                           it (compared to when we found it in the ucountrytranslate[]
                                           table) */
            if(iStatusFlag & FLAG_NLS_MESSAGES_REQUESTED)
                displayMessage(ERROR_NLSMSG_NOT_EXIST, 1, (int)acMessageFileNls);
            strcpy(acMessageFileNls, acMessageFileUs);
            }
        else
                                        /* The NLS message file does exist, so any problem retrieving
                                           messages is caused by invalid contents of that file, which
                                           we should inform the user for */
            iStatusFlag|=FLAG_NLS_MESSAGES_FOUND;
        }
                                        /* Process further depending on the arguments specified */
    if(iArgc==1)
        {
                                        /* If no argument is specified, display simple help */
        displayMessage(MSG_LOGO);
        displayMessage(MSG_DESCRIPTION);
        displayMessage(MSG_PARAMETERS_MISSING);
        iReturnCode=ERROR_PARAMETERS_MISSING;
        }
    else
        {
                                        /* At least one option was specified */
        displayMessage(MSG_LOGO);
                                        /* If the language was the only (two) arguments, display
                                           simple help */
        if((iArgc==3) && (iStatusFlag & FLAG_NLS_MESSAGES_REQUESTED))
            {
            displayMessage(MSG_DESCRIPTION);
            displayMessage(MSG_PARAMETERS_MISSING);
            iReturnCode=ERROR_PARAMETERS_MISSING;
            throw(iReturnCode);
            }
        if(checkCommandlineOption("?")!=0)
            {
            displayMessage(MSG_PARAMETERS_INVALID);
            displayMessage(MSG_PARAMETERS_TEXT);
            iReturnCode=ERROR_PARAMETERS_INVALID;
            }
        else
            {
                                        /* Now just find all commandline parameters and trow
                                           an error if an invalid combination was found */
            try
                {
                matchParameters();
                }
            catch(int iErrorCode) 
                {
                displayMessage(iErrorCode);
                displayMessage(MSG_PARAMETERS_TEXT);
                iReturnCode=iErrorCode;
                throw(iReturnCode);
                }
                                        /* Now that we have found valid commandline
                                           parameters, process them */
            try
                {
                processParameters();
                }
            catch(int iErrorCode)
                {
                displayMessage(iErrorCode);
                iReturnCode=iErrorCode;
                throw(iReturnCode);
                }
            }
        }

    return(*this);
}
/**
 * Function representing the <prim_prime> productions
 */
attr RecursiveDescentParser::prim_prime(TableEntry* pTabEntry) {
	attr retval;
	retval.type = T_ERROR;
	
	if(errorCondition) return retval;
	if(token == TK_LEFT_BRACKET) 
	{
#if DEBUG_PARSER
		std::cout << "<prim_prime> --> [<exp>]\n";
#endif
		token = scanner->getToken();
		
		retval = exp();
		retval.attrib = VA_SIMPLE;
		
		match(TK_RIGHT_BRACKET);
	}
	else if(token == TK_LEFT_PARENTHESES)
	{
#if DEBUG_PARSER
		std::cout << "<prim_prime> --> (<o_list>)\n";
#endif
		Token sToken = token;
		token = scanner->getToken();
		ParamList* pList = o_list();
		match(TK_RIGHT_PARENTHESES);

		if(pTabEntry && pTabEntry->getEntryType()==TableEntry::FUNCTION) {
			FunctionEntry* fe = (FunctionEntry*)pTabEntry;
			if(pList) {
				matchParameters(fe, pList, sToken);
			}
			retval.type = fe->getReturnType();
			retval.addr = symTab.getNextAddress();

			iCode.threeAddressCode(TAC_PARAM, pList);
			iCode.threeAddressCode(retval, TAC_CALL, fe->getLabel(), fe->getParamCount());
		}
		else {
			std::stringstream errorMsg;
			errorMsg << "'" << pTabEntry->getName() << "' is not a function";
			errorHandler(errorMsg.str(), sToken);
		}
	}
	else if( token == TK_ASTERISK || 
			token == TK_SLASH || 
			token == TK_PERCENT || 
			token == TK_PLUS ||
			token == TK_MINUS || 
			token == TK_RIGHT_PARENTHESES || 
			token == TK_RIGHT_BRACKET || 
			token == TK_SEMICOLON || 
			token == TK_LT || 
			token == TK_GT || 
			token == TK_LTE || 
			token == TK_GTE || 
			token == TK_EQUAL || 
			token == TK_NOT_EQ ) 
	{		
#if DEBUG_PARSER
		std::cout << "<prim_prime> --> e\n";
#endif
		retval = pTabEntry->getAttr();
	}
	else {
		errorHandler();
	}
	
	return retval;
}