コード例 #1
0
ファイル: exp_ifloop.c プロジェクト: nickgn12/neshla
BOOL FASTCALL comProc_IfLoop(U16 flags, S16 *brackCnt)
{
    BOOL        BRACK=FALSE,FAR_BRANCH=FALSE,FLIPOP;
    S32         start,whilestart,offset;
    BANK        *bank;
    U8          *condPtr,*elsePtr;
    int         index,mode;

    CheckCurBank();

    if((mode=StrInStrint(szTemp,siIffys))!=-1) {

        if(mode==IFMODE_DOWHILE) {  
            bank        = curBank;
            start       = GetBankOffset();
            if(STRCMP(GetNextWord(),"while")) {
                // 'ist der code block!
                GetCode(flags|CF_BRACEOK, brackCnt);
                if(STRCMP(GetNextWord(),"while"))
                    error(ERR_WHILEEXP,szTemp);
            }
        }

        if(GetNextWord()[0]!='(')
            error(ERR_INVCOND,szTemp);
        else {
            GetNextWord();
            BRACK = TRUE;
        }

        USE_DEFS        = FALSE;
        if(!STRCMP(szTemp,"far")) {
            FAR_BRANCH = TRUE;
            GetNextWord();
        } else if(!STRCMP(szTemp,"near")) {
            GetNextWord();
        }

        // parse the "is" "is not" "not" "no", etc.
        FLIPOP = FALSE;
        while((index=StrInStrint(szTemp,siIsNot))!=-1) {
            if(!siIsNot[index].index)
                FLIPOP = !FLIPOP;
            GetNextWord();
        }
                            
        USE_DEFS        = TRUE;
        if(!PRECOMPILING) {   
            if((index=StrInStrint(szTemp,siConditions))==-1) {
                error(ERR_INVALIDCOND,szTemp);
                condPtr = NULL;
            } else {
                if(mode==IFMODE_IF || mode==IFMODE_WHILE)
                    FLIPOP = !FLIPOP;
                index = (FLIPOP)?
                    RelSwapOp(siConditions[index].index):
                    siConditions[index].index;

                if(mode==IFMODE_WHILE)
                    whilestart = GetBankOffset();

                if(FAR_BRANCH) {
                    WriteOpcodeB(RelSwapOp(index),3);
                    WriteOpcode(opJMP_ABS);
                    condPtr = curBank->ptr;
                    WriteCodeW(0);
                } else {
                    condPtr = curBank->ptr+1;
                    WriteOpcodeB(index,0);
                }
            }    
            if(mode!=IFMODE_DOWHILE) {
                bank    = curBank;
                start   = GetBankOffset();
            }
        }
                         
        if(BRACK && GetNextWord()[0]!=')') {
            error(ERR_IFCONDCLOSEEXP,szTemp);
        }
          
        if(mode!=IFMODE_DOWHILE)
            GetCode(flags|CF_BRACEOK|CF_GETNEXTWORD, brackCnt);

        elsePtr = NULL;
        if(!STRCMP(PeekNextWord(),"else")) {
            GetNextWord();
            if(mode!=IFMODE_IF)
                error(ERR_ONLYIFSELSE);
            else {         
                if(!PRECOMPILING)
                    WriteOpcode(opJMP_ABS);
                elsePtr = curBank->ptr;
                if(!PRECOMPILING)
                    WriteCodeW(0);
            }
        }

        if(!PRECOMPILING) {
            if(bank     != curBank)
                error(ERR_FOREVEROUTOFBANK,bank->label,curBank->label);
            else if(condPtr) {
                if(mode==IFMODE_WHILE) {
                    WriteOpcodeW(opJMP_ABS,whilestart);
                }
                if(FAR_BRANCH) {  
                    if(mode==IFMODE_DOWHILE) {
                        PUTW(condPtr,start);
                    } else {
                        PUTW(condPtr,GetBankOffset());
                    }
                } else {
                    offset = mode==IFMODE_DOWHILE?
                        start-GetBankOffset():
                        GetBankOffset()-start;

                    if((offset<-128 || offset>127))
                        error(ERR_BRANCHOUTOFRANGE);
                    else
                        PUTB(condPtr,(U8)offset);
                }
            }
        }
        if(elsePtr) {
            GetCode(flags|CF_BRACEOK|CF_GETNEXTWORD, brackCnt);
            if(!PRECOMPILING)
                PUTW(elsePtr,GetBankOffset());
        }

    } else if(!STRCMP(szTemp,"forever")) {

        bank    = curBank;
        start   = GetBankOffset();

        GetCode(flags|CF_BRACEOK|CF_GETNEXTWORD, brackCnt);

        if(bank != curBank)
            error(ERR_FOREVEROUTOFBANK,bank->label,curBank->label);
        else
            WriteOpcodeW(opJMP_ABS,start);

    } else
        return FALSE;
    return TRUE;
}
コード例 #2
0
ファイル: exp_vardeclare.c プロジェクト: irbrad/NESHLA
BOOL FASTCALL comProc_VarDeclare(U16 flags, S16 *brackCnt)
{
	int cast,arraySize,elementsSize,braceCnt;
    S32 offset=-1,elementsEnd;
    S32 num;
    U16 varflags = 0;
    char *label=NULL;
    VAR *castvar=NULL;
    VAR *var=NULL,*pvar;
    BOOL VARSET, SEEKED = FALSE;

    if(!STRCMP(szTemp,"typedef")) {
     	varflags |= VARFLAG_TYPECAST; 
        GetNextWord();
    }

    if(!STRCMP(szTemp,"shared")) {
     	varflags |= VARFLAG_SHARED;
        GetNextWord();
    }

	if((cast=IsVarCast(szTemp,&castvar))==VARCAST_NULL) {
    	if(varflags&VARFLAG_TYPECAST) {
        	error(ERR_NOTTYPECAST,szTemp);
         	return TRUE;
        }
    	return FALSE;
    }

    if(curVar&&(curVar->flags&VARFLAG_TYPECAST))
    	varflags |= VARFLAG_TYPECAST;

    for(;;) {
		if(!IsStringLabel(GetNextWord())) {
			error(ERR_BADLABEL,szTemp);
        	sprintf(szTemp, "invlabel_%04X", invlabel++);
		} else {
         	if(PRECOMPILING && IsLabelUsed(szTemp,curVar?curVar->childVars:vars))
        		sprintf(szTemp, "invlabel_%04X", invlabel++);
        }
    	label = strdup(szTemp);

    	if(PeekNextWord()[0]==':') {
    		GetNextWord();
			if(IsStrNum(GetNextWord())) {
				offset = ConfirmWord(StrToInt(szTemp));  
     			varflags |= VARFLAG_FIXED;
			} else
				error(ERR_INTEXP);
            VARSET = TRUE;
    	} else {
			if(varflags&VARFLAG_TYPECAST)
				VARSET = TRUE;
			else if(!curBank)
    			fatal(FTL_VARNOTROMBANK);
		
    		if(cast == VARCAST_STRUCT && !(varflags & VARFLAG_TYPECAST) && !PRECOMPILING) {
    			offset = GetBankOffset();
				VARSET = TRUE;
            } else
            	VARSET = FALSE;
        }

    	if(PRECOMPILING) {
    		var = AddVariable(label, cast, castvar, varflags, offset);
            if(varflags&VARFLAG_TYPECAST) {
            	if(curVar) {
        			var->offset		= VarSize(curVar);
                }
        	}
		} else {
    		var = FindVariable(curVar?curVar->childVars:(varflags&VARFLAG_TYPECAST)?typedefs:vars, label);
            if(!(var->flags&VARFLAG_TYPECAST) && (!(var->flags&VARFLAG_DEFCASTED) || cast!=VARCAST_STRUCT) && (var->offset==-1))
            	SetVarOffsets(var,GetBankOffset(),FALSE);
    	}
		if(castvar) {
            var->size = castvar->size;
        }

        arraySize = 0;
    	if(PeekNextWord()[0]=='[') {
    		GetNextWord();
            if(PeekNextWord()[0]==']') {
            	arraySize=-1;//autosize
    			GetNextWord();
            } else {          /*
				if(IsStrNum(szTemp)) {
            	    if(((var->flags&VARFLAG_TYPECAST) && PRECOMPILING) || (!(var->flags&VARFLAG_TYPECAST))) {
                		arraySize = ConfirmWord(StrToInt(szTemp));
						var->arraySize = arraySize;
                	}
				} else
					error(ERR_INTEXP);
                    */
				CompileImmediateInteger(0, &num, -1, 0);
                if(((var->flags&VARFLAG_TYPECAST) && PRECOMPILING) || (!(var->flags&VARFLAG_TYPECAST))) {
            		arraySize = ConfirmWord(num);
            		var->arraySize = arraySize;
                }
    			if(GetNextWord()[0]!=']')
					error(ERR_ARRAYENDEXP,szTemp);
            }
    	}

        if(!(var->flags&VARFLAG_DEFCASTED) && (cast==VARCAST_STRUCT)) {
    		SetCurVar(var);
			GetCode(flags|CF_BRACEOK|CF_GETNEXTWORD, brackCnt);
			ReleaseCurVar();
        } else {
        	if(PeekNextWord()[0]=='=') {
    			GetNextWord();
				if(var->flags&VARFLAG_TYPECAST) {
            		error(ERR_VARCASTASSIGN,label);
                	SeekPastBraceBlock();
            	} else if(curBank->type==BANKTYPE_RAM) {
                	error(ERR_VARDECLAREINRAM);
                	SeekPastBraceBlock();
                } else {
                          
					elementsSize	= 0;
	                elementsEnd		=
	                	(GetBankOffset()-curBank->org) +
	                    ((arraySize==-1)?
	                    	var->size:var->size*arraySize);

     				if(GetNextWord()[0]=='{') {
                    	if(!arraySize) {
                         	error(ERR_NOTARRAY,var->label);
                        }
                        braceCnt = 1;
    					GetNextWord();
                    } else braceCnt = 0;
                    do {
                    	braceCnt =
                        	CompileVarBody(flags,brackCnt, var, &elementsSize, braceCnt, cast);
                    } while(braceCnt);

                    if(!PRECOMPILING) {
                    	if(arraySize==-1) {
                    		arraySize=elementsSize/VarSize(var);
                        	SEEKED = TRUE;
                    	} else {
                    		if(elementsSize>VarSize(var))
                    			error(ERR_ELEMENTSTOOLARGE,var->label,elementsSize-VarSize(var));
                			BankSeek(elementsEnd);
                        	SEEKED = TRUE;
                   		}
              			var->arraySize = arraySize;
                    }

                }
        	} else {
             	if(((var->flags&VARFLAG_TYPECAST) && PRECOMPILING) || (!(var->flags&VARFLAG_TYPECAST) && !PRECOMPILING && !VARSET)) {
              		if(arraySize==-1)
                    	arraySize = 1;
                    if(arraySize!=0)
                    	var->arraySize = arraySize;
                	if(!PRECOMPILING) {
						BankSeekFwd(VarSize(var));
                        SEEKED = TRUE;
                    }
                }
            }
            if(((var->flags&VARFLAG_TYPECAST) && PRECOMPILING) || (!(var->flags&VARFLAG_TYPECAST) && !PRECOMPILING)) {
            	// adjust all the var sizes for structs
            	arraySize = VarSize(var);
                pvar = var->parent;
                while(pvar) {
                 	pvar->size += arraySize;
                    pvar = pvar->parent;
                }
            }
        }
		if(!(var->flags&VARFLAG_TYPECAST) && (cast==VARCAST_STRUCT))
			SetVarOffsets(var,offset,FALSE);
        // removed 2004-05-22, if problems occurs, check
        if(!SEEKED && (var->flags&(VARFLAG_TYPECAST|VARFLAG_DEFCASTED))==VARFLAG_DEFCASTED && (cast==VARCAST_STRUCT)) {
        	CheckCurBank();
            if((var->flags&VARFLAG_TYPECAST) || !PRECOMPILING)
            	BankSeekFwd(VarSize(var));
        }           
    	ssFree(label);
        
        if(PeekNextWord()[0]!=',')
        	break;
        GetNextWord();
    }

    return TRUE;
}