📄 masmber_c6.cpp
字号:
AsmFn->InsertAsmLine(newln,line); // 插入。
} // endif
DebugKit(printf("\nInclude [%s]...",p->Name()); Debugkey;); // debug
// 在INCLUDE的文件中,不能出现首要控制命令!
err = MC_Include(p->Name); // p->Name装有文件名。
// err, line, p 带值返回。
} // end Case_Include_Do
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 把一个Token->Name中的字串分析后转化成一条新的Token链。返回链指针。
// 需要使用Ln。使用AsmFn->CommentEnable。
// 注意: 他会创建(new)一个新链,但不负责(delete)它。
// err值输入时应该是OK_no_Err的。
//---------------------------------------------------------------------------
AsmLine* MacroAsmber::TokenNameToNewLn(ERR &err, Tokenfield* pt)
{ if(pt->Name.IsEmpty())
{ OutputErr(MissParasErr); err = Have_Errs; return NULL; } // endif
AsmLine* oldLn = Ln; // 保存Ln值。
Ln = new AsmLine; // 创建新汇编行。
Ln->LineNo = oldLn->LineNo; // 复制行号。
// 调用词法分析子程序,把字串转化成Token流。这其中用到Ln。
char ss[256];
Jassert(pt->Name.getLen()<255);
err = StrToToken(pt->Name.makeStr(ss), AsmFn->CommentEnable); // 分析参数。
register AsmLine* ln = Ln; Ln = oldLn; // 恢复Ln值。
pt->Name.Removal();
return ln;
} // end TokenNameToNewLn
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 需要使用Ln。使用AsmFn->CommentEnable。
//---------------------------------------------------------------------------
void MacroAsmber::Case_Reset_Do(ERR &err, Tokenfield* pt)
{ err = OK_no_Err;
AsmLine* ln = TokenNameToNewLn(err, pt);
// 把一个pt->Name中的字串分析后转化成一条新的Token链。返回链指针。
if(!err)
{ // Now, 得到一个Token链。
if(ln->FirstTkn() != NULL)
{ for( pt = ln->head; pt->next; ) // ... ',' + Word ....
{ err = TokenOper::ArgvWordParser(pt); // 看它是不是一个WordList。
if(err) { OutputErr(err); break; } // endif
pt = pt->next; // Now pt->Token == WordSToken
MvList->UpdateVar(pt->Name, 0); // 登记该变量。
} // end for pt
} // endif
else
{ OutputErr(MissParasErr); err = Have_Errs; } // end else
} // endif
delete ln; // 释放内存。
} // end Case_Reset_Do
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 需要使用Ln。使用AsmFn->CommentEnable。
//---------------------------------------------------------------------------
void MacroAsmber::Case_Set_Do(ERR &err, Tokenfield* pt)
{ err = OK_no_Err;
AsmLine* ln = TokenNameToNewLn(err, pt);
// 把一个pt->Name中的字串分析后转化成一条新的Token链。返回链指针。
if(!err)
{ // Now, 得到一个Token链。
if(ln->FirstTkn() != NULL)
{ for( pt = ln->head; pt->next; ) // ... ',' + Word ....
{ err = TokenOper::ArgvWordEvluParser(pt); // 看它是不是一个WordEvluList。
if(err) { OutputErr(err); break; } // endif
pt = pt->next; // Now pt->Token == WordSToken
MvList->UpdateVar(pt->Name, (int16u)pt->Value); // 登记该变量。
} // end for pt
} // endif
else
{ OutputErr(MissParasErr); err = Have_Errs; } // end else
} // endif
delete ln; // 释放内存。
} // end Case_Set_Do
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 用于$IF和$ELSEIF语句中的语法分析。
// 分析pt->next。
//---------------------------------------------------------------------------
ERR MacroAsmber::MroIF_NeedOneExpr(Tokenfield* pt)
{ ERR err;
int8 count = TokenOper::CalExpNum(pt, err);
if(err) { return err; } // endif
switch(count)
{ case 0 : return ArguInsufErr;
case 1 : return OK_no_Err;
default : return ArguExcevErr;
} // end switch
} // end MroIF_NeedOneExpr
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// pt 所指向的就是 $IF 节点。 err带值返回。
//---------------------------------------------------------------------------
void MacroAsmber::Case_MroIF_Do(ERR &err, Tokenfield* pt)
{ if(++MroIfNest > MaxMroIfNest)
{ OutputErr(IfElseNestOutErr); err = Have_Errs; return; } // endif
err = OK_no_Err;
pt->Token = IF_Tn; // Token升级。
pt->loc[1] = MroIfNest; // 暂存IF语句的嵌套层数
if(MroIfStack.GetXorTop()) { return; } // endif 如果上层状态被ban
AsmLine* ln = TokenNameToNewLn(err, pt);
// 把一个pt->Name中的字串分析后转化成一条新的Token链。返回链指针。
if(err) { goto ret; } // endif
// Now, 得到一个Token链。
// 语法分析。
err = MroIF_NeedOneExpr(ln->head);
if(err) { goto ret; } // endif
// Now, IF expr has passed the parse.
pt->Token2 = MvList->CalVarExpr(err, ln->head->next->ExpPt); // 计算数值表达式。
if(err) { OutputErr(err); goto dele; } // endif
// 结果存放在pt->TOken2中。
MroIfStack.push( true, (bool)pt->Token2 ); // 把状态压栈!!
dele:
TokenOper::DelExpTkn(ln->FirstTkn()); // 释放Expr内存。
ret:
delete ln; // 释放内存。
} // end Case_MroIF_Do
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// pt 所指向的就是 $ELSEIF 节点。 err带值返回。
//---------------------------------------------------------------------------
void MacroAsmber::Case_MroELSEIF_Do(ERR &err, Tokenfield* pt)
{ err = OK_no_Err;
pt->Token = ELSEIF_Kn; // Token升级!
pt->Token2 = 0;
pt->loc[1] = MroIfNest; // 暂存IF语句的嵌套层数
if(MroIfNest == 0)
{ OutputErr(ESIFMisplaceErr); err = Have_Errs; return; } // endif
if(MroIfNest > MroIfStack.getSP()) { return; } // 如果ELSEIF是不属于本层的
// Now, ELSEIF确实是属于本层的
if(MroIfStack.getB()) // 如果ELSEIF上面的IF语句中的表达式为真的话
{ MroIfStack.settop(false, true); return; } // endif
// ELSEIF上面的IF语句没有执行,即IF表达式的值为假
AsmLine* ln = TokenNameToNewLn(err, pt);
// 把一个pt->Name中的字串分析后转化成一条新的Token链。返回链指针。
if(err) { goto ret; } // endif
// Now, 得到一个Token链。
// 语法分析。
err = MroIF_NeedOneExpr(ln->head);
if(err) { goto ret; } // endif
// Now, IF expr has passed the parse.
pt->Token2 = MvList->CalVarExpr(err, ln->head->next->ExpPt); // 计算数值表达式。
if(err) { OutputErr(err); goto dele; } // endif
// 结果存放在pt->TOken2中。
MroIfStack.settop(true, (bool)pt->Token2); // 把状态压栈!!
dele:
TokenOper::DelExpTkn(ln->FirstTkn()); // 释放Expr内存。
ret:
delete ln; // 释放内存。
} // end Case_MroELSEIF_Do
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// 次要汇编控制指令语法分析器。
//---------------------------------------------------------------------------
ERR MacroAsmber::DogCtrlParse(AsmLine* &line)
{ ERR erra = OK_no_Err;
Tokenfield* pt;
line->Enable = false; // 把$行禁用。
for( pt = line->head; pt->next; pt = pt->next ) // 一个Token一个Token地扫描。
{ ERR err = OK_no_Err;
register Tokenfield* p = pt->next;
if(p->Token != Dog_Ctrl)
{ OutputErr(DogCtrlIllErr); erra = Have_Errs; break; } // endif
switch(p->Token2)
{ case INCLU_Tn:
{ Case_Include_Do(err, line, p);
p->Token2 = Dog_Skip; break; // 不把它删除是因为报错处理。
} // end case
case SET_Tn:
{ Case_Set_Do(err, p);
p->Token2 = Dog_Skip; break;
} // end case
case RESET_Tn:
{ Case_Reset_Do(err, p);
p->Token2 = Dog_Skip; break;
} // end case
case IF_Tn:
{ Case_MroIF_Do(err,p);
p->Token2 = Dog_Skip; break;
} // end case
case ENDIF_Tn:
{ pt->Token = ENDIF_Tn; // Token升级。
pt->loc[1] = MroIfNest;
if(--MroIfNest < 0)
{ OutputErr(ENDIFMisplaceErr); MroIfNest = 0; return Have_Errs; } // endif
if(MroIfNest < MroIfStack.getSP()) { MroIfStack.pop(); } // endif
p->Token2 = Dog_Skip; break;
} // end case
case ELSE_Tn:
{ pt->Token = ELSE_Tn; // Token升级。
pt->loc[1] = MroIfNest;
if(MroIfNest == 0)
{ OutputErr(ELSEMisplaceErr); return Have_Errs; } // endif
pt->Token2 = MroIfStack.getB();
if(MroIfNest <= MroIfStack.getSP())
{ MroIfStack.settop(false, (bool)pt->Token2); } // endif
break;
} // end case
case ELSEIF_Tn:
{ Case_MroELSEIF_Do(err,p);
p->Token2 = Dog_Skip; break;
} // end case
case LI_Tn : break; // Just pass through
case NOLI_Tn : break; // Just pass through
case GEN_Tn : break; // Just pass through
case NOGEN_Tn : break; // Just pass through
case SAV_Tn : break; // Just pass through
case RSTO_Tn : break; // Just pass through
case EJECT_Tn : break; // Just pass through
case Dog_Skip : break; // this statement should not write, just for Debug
default: { erra = Have_Errs;
EThrows(printf("\nDogCtrlParse out of run!"); Debugkey;); // debug
} // end default
} // end switch
if(err) { erra = Have_Errs; } // endif
} // end for
return erra;
} // end DogCtrlParse
//---------------------------------------------------------------------------
//---------------------------------------------------------------------------
// end MAsmber_C6.cpp
//---------------------------------------------------------------------------
// Written by JamesyFront. ZLGmcu Dev.Co.Ltd. 2002.
//---------------------------------------------------------------------------
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -