📄 cgen.cpp
字号:
if(p2) generate_stmt(p2);
strcpy(register1,"ax");
if(p2) strcpy(register2,"bx");
if(strcmp(pa_exp->m_strIDname,"+")==0){
READTWO //宏,读取两个源操作数。
AllGlobals.code.write("\nadd\t",5);
AllGlobals.code.write(register1,2);
AllGlobals.code.write(",",1);
AllGlobals.code.write(register2,2); //两个源操作数相加,结果入栈。
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
else if(strcmp(pa_exp->m_strIDname,"-")==0
|| strcmp(pa_exp->m_strIDname,"!=")==0){
READTWO
AllGlobals.code.write("\nsub\t",5);
AllGlobals.code.write(register1,2);
AllGlobals.code.write(",",1);
AllGlobals.code.write(register2,2);
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
else if(strcmp(pa_exp->m_strIDname,"*")==0){
READTWO
AllGlobals.code.write("\nmul\t",5);
AllGlobals.code.write(register2,2);
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
else if(strcmp(pa_exp->m_strIDname,"/")==0){
READTWO
AllGlobals.code.write("\ndiv\tbx\n",8);
AllGlobals.code.write("cbw\t",4); //除法所得的商要进行位扩展。
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
else if(strcmp(pa_exp->m_strIDname,"=")==0){
READTWO
AllGlobals.code.write("\nmov\t",5);
AllGlobals.code.write(pa_exp->m_pchild[0]->m_strIDname,
strlen(pa_exp->m_pchild[0]->m_strIDname));
AllGlobals.code.write(",",1);
AllGlobals.code.write(register2,2);
}
else if(strcmp(pa_exp->m_strIDname,"<")==0 ||
strcmp(pa_exp->m_strIDname,"<=")==0
|| strcmp(pa_exp->m_strIDname,"==")==0){
READTWO
AllGlobals.code.write("\nsub\t",5);
AllGlobals.code.write(register1,2);
AllGlobals.code.write(",",1);
AllGlobals.code.write(register2,2);
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
else if(strcmp(pa_exp->m_strIDname,">")==0 ||
strcmp(pa_exp->m_strIDname,">=")==0){
READTWO
AllGlobals.code.write("\nsub\t",5);
AllGlobals.code.write(register2,2);
AllGlobals.code.write(",",1);
AllGlobals.code.write(register1,2);
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
else if(strcmp(pa_exp->m_strIDname,"!")==0){
AllGlobals.code.write("\npop\t",5);
AllGlobals.code.write(register1,2);
AllGlobals.code.write("\nnot\t",5);
AllGlobals.code.write(register1,2);
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
else if(strcmp(pa_exp->m_strIDname,"&&")==0){
READTWO
AllGlobals.code.write("\nand\t",5);
AllGlobals.code.write(register1,2);
AllGlobals.code.write(",",1);
AllGlobals.code.write(register2,2);
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
else if(strcmp(pa_exp->m_strIDname,"||")==0){
READTWO
AllGlobals.code.write("\nor\t",4);
AllGlobals.code.write(register1,2);
AllGlobals.code.write(",",1);
AllGlobals.code.write(register2,2);
AllGlobals.code.write("\npush\t",6);
AllGlobals.code.write(register1,2);
}
break;
}
}
/****************************************************************
**处理除表达式外的其他语句体。
*****************************************************************/
void Cgenerator::generator_substmt(CTreeNode* pa_Stmt){
//五个静态变量用于保存产生的符号地址。
static char temp1[41],temp2[41],temp3[41],temp4[41],temp5[41];
CTreeNode *p;
switch(pa_Stmt->kind.m_EnStmtKind){
case IfK:
generate_stmt(pa_Stmt->m_pchild[0]);
JUDGE_CONDITION(->) //判定条件表达式,
generator_unique_addr(pa_Stmt);
strcpy(temp4,pa_Stmt->m_strIDname);
AllGlobals.code.write(temp4,strlen(temp4));
generator_unique_addr(pa_Stmt);
strcpy(temp5,pa_Stmt->m_strIDname);
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(temp5,strlen(temp5));
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp4,strlen(temp4));
AllGlobals.code.write(":\n",2);
p=pa_Stmt->m_pchild[1];
while(p){
generate_stmt(p);
p=p->m_pbrother;}
if(pa_Stmt->m_pchild[2]!=NULL){ //如果有else语句。
generator_unique_addr(pa_Stmt);
strcpy(temp4,pa_Stmt->m_strIDname);
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(temp4,strlen(temp4));
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp5,strlen(temp5));
AllGlobals.code.write(":\n",2);
p=pa_Stmt->m_pchild[2];
while(p){
generate_stmt(p);
p=p->m_pbrother;}
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp4,strlen(temp4));
AllGlobals.code.write(":\n",2);
}
else{
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp5,strlen(temp5));
AllGlobals.code.write(":\n",2);
}
break;
case WhileK:
generator_unique_addr(pa_Stmt);
strcpy(temp1,pa_Stmt->m_strIDname);
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp1,strlen(temp1));
AllGlobals.code.write(":\n",2);
generator_unique_addr(pa_Stmt);
strcpy(temp2,pa_Stmt->m_strIDname);
generate_stmt(pa_Stmt->m_pchild[0]);
JUDGE_CONDITION(->)
generator_unique_addr(pa_Stmt);
strcpy(temp3,pa_Stmt->m_strIDname);
AllGlobals.code.write(temp3,strlen(temp3));
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(temp2,strlen(temp2));
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp3,strlen(temp3));
AllGlobals.code.write(":\n",2);
p=pa_Stmt->m_pchild[1];
while(p){
generate_stmt(p);
p=p->m_pbrother;}
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(temp1,strlen(temp1));
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp2,strlen(temp2));
AllGlobals.code.write(":\n",2);
break;
case ForK:
generate_stmt(pa_Stmt->m_pchild[0]);//for语句的第一个表达式初始化循环计数。
generator_unique_addr(pa_Stmt);
strcpy(temp1,pa_Stmt->m_strIDname);
generator_unique_addr(pa_Stmt);
strcpy(temp2,pa_Stmt->m_strIDname);
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp1,strlen(temp1));
AllGlobals.code.write(":\n",2);
generate_stmt(pa_Stmt->m_pchild[0]->m_pbrother);//第二个为条件句。
JUDGE_CONDITION(->m_pbrother->)
generator_unique_addr(pa_Stmt);
strcpy(temp3,pa_Stmt->m_strIDname);
AllGlobals.code.write(temp3,strlen(temp3));
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(temp2,strlen(temp2));
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp3,strlen(temp3));
AllGlobals.code.write(":\n",2);
generate_stmt(pa_Stmt->m_pchild[0]->m_pbrother->m_pbrother);
p=pa_Stmt->m_pchild[1];
while(p){
generate_stmt(p);
p=p->m_pbrother;}
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(temp1,strlen(temp1));
AllGlobals.code.write("\n",1);
AllGlobals.code.write(temp2,strlen(temp2));
AllGlobals.code.write(":\n",2);
break;
case WritebK://writeb语句只写一个字符,可直接调用中断进行。
if(pa_Stmt->m_pchild[0]->kind.m_EnExpKind==ConstK &&
pa_Stmt->m_pchild[0]->m_EnTypevalue==CCHAR){
AllGlobals.code.write("\nmov\tah,2h",10);//字符要加单引号,
AllGlobals.code.write("\nmov\tdl,'",9);
AllGlobals.code.write(pa_Stmt->m_pchild[0]->m_strIDname,1);
AllGlobals.code.write("'",1);}
else if(pa_Stmt->m_pchild[0]->kind.m_EnExpKind==ConstK){
AllGlobals.code.write("\nmov\tah,2h",10);//数字将作为ascII码值处理。
AllGlobals.code.write("\nmov\tdl,",8);
AllGlobals.code.write(pa_Stmt->m_pchild[0]->m_strIDname,
strlen(pa_Stmt->m_pchild[0]->m_strIDname));}
else{
generate_stmt(pa_Stmt->m_pchild[0]);
AllGlobals.code.write("\npop\tax",7);
AllGlobals.code.write("\nmov\tah,2h",10);
AllGlobals.code.write("\nmov\tdx,ax",10);}
AllGlobals.code.write("\nint\t21h",8);
break;
case WritedK://writed只要对参数调用显示例程即可。
generate_stmt(pa_Stmt->m_pchild[0]);
AllGlobals.code.write("\nCall\tShow@@Show",16);
break;
case GotoK:
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(pa_Stmt->m_pchild[0]->m_strIDname,
strlen(pa_Stmt->m_pchild[0]->m_strIDname));
break;
case AddressK:
AllGlobals.code.write("\n",1);
AllGlobals.code.write(pa_Stmt->m_pchild[0]->m_strIDname,
strlen(pa_Stmt->m_pchild[0]->m_strIDname));
AllGlobals.code.write(":",1);
break;
case BreakK://break语句跳到循环控制语句的结尾处。
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(temp2,strlen(temp2));
break;
case ContinueK://continue语句跳到循环控制语句的起始处。
AllGlobals.code.write("\njmp\t",5);
AllGlobals.code.write(temp1,strlen(temp1));
break;
case ReturnK:
if(strcmp(pa_Stmt->m_strScope,"main")!=0)
AllGlobals.code.write("\npop\tbp",7);
if(pa_Stmt->m_pchild[0] && strcmp(pa_Stmt->m_strScope,"main")!=0)
generate_stmt(pa_Stmt->m_pchild[0]);
if(pa_Stmt->m_pbrother!=NULL ||//return后面还有语句,则必须写上ret,否则函数结束时
(pa_Stmt->m_pfather->m_Ennodekind!=FuncK //由函数自己负责。
&& pa_Stmt->m_pfather->m_pbrother!=NULL)){
if(strcmp(pa_Stmt->m_strScope,"main")!=0)
AllGlobals.code.write("\npush\tbp",9);
AllGlobals.code.write("\nret\n",5);}
break;
case CallK:
p=pa_Stmt->m_pchild[1];
while(p){
generate_stmt(p);
p=p->m_pbrother;}//依次处理函数调用里的所有实参。
AllGlobals.code.write("\ncall\t",6);
AllGlobals.code.write(pa_Stmt->m_pchild[0]->m_strIDname,strlen(pa_Stmt->m_pchild[0]->m_strIDname));
break;
}
}
/****************************************************************
**用于为代码产生唯一的符号地址,符号地址的格式为:
**"作用域@@序号"
****************************************************************/
void Cgenerator::generator_unique_addr(CTreeNode *pa_name){
char temp[5];
strcpy(pa_name->m_strIDname,pa_name->m_strScope);
strcat(pa_name->m_strIDname,"@@");
itoa(m_iunique,temp,5);
m_iunique++;
strcat(pa_name->m_strIDname, temp);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -