?? 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 + -