📄 labelmaniger_c.cpp
字号:
Lab.SetValue(result->val); // ValueOK
return OK_no_Err; // OK
} // end CalLabValChk
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 给出一个ExpToken指向的表达式的头指针,根据表达式计算结果.
// err = 0, 成功返回。
// ----- 来自OPAct's err: -----
// err = BadRelExp
// err = IllExpTypOp
// err = DividedByZero
// err = BitAddrOutRange
// err = ShiftsOverflow
// ----- 来自OPNDAct's err: -----
// err = LabNotExist 10 (Pass x)
// err = LabNotReady 11
// err = LabValNotOk 12 (??? printf)
//---------------------------------------------------------------------------
#define getOpKn OpKn = ( Pt ? Pt->Token : ' ' );
#define getNextOp Pt = Pt->next; getOpKn
//---------------------------------------------------------------------------
// 根据当前汇编行,pt指向的表达式,计算表达式的值,带回err值。
//---------------------------------------------------------------------------
const TriVal* LabelManager::
CalExpr(ERR &err, Tokenfield* Pt, JLabelNode *const RfLb, bool typmode)
{ static TriVal t; // 静态分配空间
DebugMsg( if(Pt == NULL) { printf("\nExpr NULL error!"); return &t; } ) // debug
if(++nest > Max_nest_depth)
{ err = StackOverFlow; masm.OutputErr(StkOverFlowErr); return NULL; } // endif
err = OK_no_Err; TokenStack optr; TriValStack opnd;
int16u OpKn;
getOpKn;
while( OpKn !=' ' || optr.Notempty() )
{ // ..................................................................
if( IsOPTR(OpKn) ) // 是个运算符
{ // 已经得到一个运算符.
// cout<<"\nget an OPTR ["<<(char)OpKn<<"].";
switch( OPsuperior( optr.gettop(), OpKn ) )
{ case '<' : { optr.push(OpKn); getNextOp; break; } // end case
case '=' : { optr.pop(); getNextOp; break; } // end case
case '>' : { err = OPTRAct(optr, opnd); // 给err赋值
if(err) { DebugMsg(puts("\nExpression error!"); Debugkey;);
return NULL; } // endif
break;
} // end case
default: { FatalErr(); } // end default
} // end switch
} // endif IsOPTR(Token)
else // 不是运算符, 而是操作数, 则进栈。根据Pt所指向的Token,给Trival赋值。
{ err = OPNDAct(Pt, t, RfLb); // 给err赋值, 带回t, t是一个TriVal结构体。
if(err) // 操作数出错
{ if( typmode ) // 如果是typmode==true, 该错误err会被丢弃。
{ return &t; } // endif 立刻返回,t有值。err有值。
if(err != LabNotReady) { return NULL; } // endif
// err == LabNotReady
if(!masm.Pass) // Pass2
{ masm.OutputErr(LabelNotReadyErr); return &t; } // 报错信息。
//else in Pass1 该错误被忽略。t仍然参加运算。
} // endif
opnd.push(t); // 入栈
getNextOp;
} // end else
// ..................................................................
} // end while
t = opnd.pop(); // No error. 得到结果。
Assert( if( Pt || !optr.empty() || !opnd.empty() )
{ printf("\nError in OPstack!!"); Debugkey; return NULL; } // endif
);
if(!typmode && !err) { err = CheckTriVal(t); } // endif // 正确性检查
return &t; // 返回指向 t 的指针。
} // end CalExpr
//---------------------------------------------------------------------------
#undef getOpKn
#undef getNextOp
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 根据Pt所指向的Token,给Trival赋值。
// 出错返回err值:
// ------ 来自CalLabelValue(). -------
// err = LabNotExist 10 (Pass x)
// err = LabNotReady 11
// err = LabValNotOk 12 (??? printf)
//---------------------------------------------------------------------------
ERR LabelManager::OPNDAct(Tokenfield* Pt, TriVal &t, JLabelNode *const RfLb)
{ // 对不同的Token做不同的动作。
switch(Pt->Token)
{ case ValueToken:
{ t.evaluate(Pt->Value, LB_NUM, 'A', NULL); // seg==NULL,表示不属于任何段
return OK_no_Err; // no error
} // end case
case RegisterKn:
{ t.evaluate(Pt->Token2, LB_REG, 'A', NULL); // seg==NULL,表示不属于任何段
return OK_no_Err; // no error
} // end case
case WordSToken:
{ ERR err;
JLabelNode* Lt = SearchLabelCal(Pt->Name, err, RfLb); // err带值返回。
// 查找并计算标号, 带回err值。也带回了指向标号的指针。
switch(err)
{ case OK_no_Err: // 标号中的Value已得到 <==> No err.
{ if(Lt->Attrb == 'E')
{ t.evaluatE(0, Lt->vv.LBLTyp, 'E', Lt->GetExtID()); return OK_no_Err; } // endif
else
{ t.evaluate(Lt->Value, Lt->vv.LBLTyp, Lt->Attrb, Lt->RefSeg); return OK_no_Err; } // end else
} // end case
case LabNotReady: // 标号中的Value未得到 <==> err == Have_Errs
{ // 错误仅仅是LabNotReady, 用虚值代替Value。(用于typemode)
t.evaluate((int16u)Lt->Value, Lt->vv.LBLTyp, Lt->Attrb, Lt->RefSeg);
return LabNotReady;
} // end case
case LabNotExist:
{ t.evaluate(0, LB_NUM, 'A', NULL);
return LabNotExist;
} // end case
default : { return err; } // with err
} // end switch
} // end case
case '$' : // 地址计数器
{ if(masm.Ln->IsOK) // 当前汇编行的地址OK
{ t.evaluate( masm.Ln->lc, // 当前行lc
masm.Ln->sgpt->GetSegType(), // 当前段类型,要求(LB_CODE==SEG_CODE)
masm.Ln->sgpt->GetRelType(),
masm.Ln->sgpt );
return OK_no_Err;
} // endif
else // (Ln->IsOK == false)
{ t.evaluate( masm.SegPt->SegLc, // 虚值
masm.SegPt->GetSegType(), // 当前段类型,要求(LB_CODE==SEG_CODE)
masm.SegPt->GetRelType(),
masm.SegPt );
return LabNotReady;
} // end else
} // end case
default: { EThrows(puts("\nOPNDAct out of run!"); Debugkey;)
return Have_Errs; } // end default
} // end switch
} // end OPNDAct
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 对TriVal进行正确性检查。
//---------------------------------------------------------------------------
ERR LabelManager::CheckTriVal(TriVal &t)
{ // 正确性检查
if(t.typ == LB_NUM) { return OK_no_Err; } // endif // no error
if(t.val < 0)
{ masm.OutWarning(NegTakeAsCplxWarn); } // endif
switch(t.typ)
{ case LB_BIT:
{ if(not8bit(t.val)) // 7 bit addr out of range. ??
{ masm.OutputErr(BitAddrOutRangeErr); return BitAddrOutRange; } // endif
break; // no error
} // end case
case LB_DATA: case LB_IDATA:
{ if(not8bit(t.val)) // 8 bit addr out of range.
{ masm.OutputErr(DATAOutRangeErr); return DATAAddrOutRange; } // endif
break; // no error
} // end case
case LB_CODE: case LB_XDATA: case LB_SEG:
{ if(not16bit(t.val))
{ masm.OutputErr(LocAddrOutRangeErr); return LocAddrOutRange; } // endif
break; // no error
} // end case
case LB_REG:
{ if( t.val < _R0 || t.val > _A_PC )
{ masm.OutputErr(REGOutRangeErr); return REGOutRange; } // endif
break; // no error
} // end case
default : { EThrows(cout<<"\nCheckTriVal out of run!"; Debugkey;)
return Have_Errs; } // end default
} // end switch
return OK_no_Err;
} // end CheckTriVal
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
#define pop2AndAct(func); \
TriVal b = opnd.pop(); \
TriVal a = opnd.pop(); \
err = func(a, b, a); \
if(err) { return err; } \
opnd.push(a);
//---------------------------------------------------------------------------
#define pop1AndAct(func); \
TriVal a = opnd.pop(); \
err = func(a); \
if(err) { return err; } \
opnd.push(a);
//---------------------------------------------------------------------------
#define pop_And_Call(func); \
TriVal a = opnd.pop(); \
err = func(a, optr); \
if(err) { return err; } \
opnd.push(a);
//---------------------------------------------------------------------------
ERR LabelManager::OPTRAct(TokenStack &optr, TriValStack &opnd)
{ ERR err;
switch(optr.pop())
{ // 双目运算
case '+' : { pop2AndAct(OPAdd); break; } // end case
case '-' : { pop2AndAct(OPSub); break; } // end case
case '*' : { pop2AndAct(OPMul); break; } // end case
case '/' : { pop2AndAct(OPDiv); break; } // end case
case '%' : { pop2AndAct(OPMod); break; } // end case
case '.' : { pop2AndAct(OPDot); break; } // end case
case AND : { pop2AndAct(OPAnd); break; } // end case
case OR : { pop2AndAct(OPOr); break; } // end case
case XOR : { pop2AndAct(OPXor); break; } // end case
case '=' : { pop2AndAct(OPEqu); break; } // end case
case '<' : { pop2AndAct(OPLes); break; } // end case
case '>' : { pop2AndAct(OPGrt); break; } // end case
case GRtEQUKen: { pop2AndAct(OPGrtEqu); break; } // end case
case LessEQUKn: { pop2AndAct(OPLesEqu); break; } // end case
case NotEqual : { pop2AndAct(OPNotEqu); break; } // end case
case SHL : { pop2AndAct(OPShl); break; } // end case
case SHR : { pop2AndAct(OPShr); break; } // end case
// 单目运算
case NOT : { pop1AndAct(OPNot); break; } // end case
case HIGH: { pop_And_Call(OPHigh); break; } // end case
case LOW: { pop_And_Call(OPLow); break; } // end case
case SingleNeg : { pop1AndAct(OPNeg); break; } // end case
case SinglePlus: { pop1AndAct(OPPlus); break; } // end case
default : EThrows(cout<<"\nOPTR ACT out of run!!";) Debugkey; return UnknownOPs;
} // end switch
return OK_no_Err;
} // end OPTRAct
//---------------------------------------------------------------------------
#undef pop2AndAct
#undef pop1AndAct
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// HIGH A
//---------------------------------------------------------------------------
ERR LabelManager::OPHigh(TriVal &a, TokenStack& optr)
{ if(not16bit(a.val)) // Only can "HIGH" data <= 16-bit
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -