📄 pl.cpp
字号:
ENTERID("",VARIABLE,NOTYP,0);
ENTERID("char",TYPEL,CHARS,1);
ENTERID("integer",TYPEL,INTS,1);
ENTERID("boolean",TYPEL,BOOLS,1);
ENTERID("false",KONSTANT,BOOLS,0);
ENTERID("true",KONSTANT,BOOLS,1);
ENTERID("read",PROCEDURE,NOTYP,1);
ENTERID("write",PROCEDURE,NOTYP,2);
BTAB[0].last=TX;
BTAB[0].lastPar=1;
BTAB[0].pSize=0;
BTAB[0].vSize=0;
}
void ASSIGNMENT(SYMLIST * list) //分析赋值语句
{
TYPEITEM typeItem1,typeItem2;
int i;
i=GETPOSITION(CurSymbol->value.lpValue);
if(i==0)
error(33); //标识符没有定义
else
{
if (NAMETAB[i].kind!=VARIABLE) //':='左边应该是变量
{
error(16); //应该是变量
i=0;
}
getASymbol();
typeItem1.typ=NAMETAB[i].type;
typeItem1.ref=NAMETAB[i].ref;
if(NAMETAB[i].normal)
GEN(LODA,NAMETAB[i].level,NAMETAB[i].unite.address);
else
GEN(LOD,NAMETAB[i].level,NAMETAB[i].unite.address);
if(CurSymbol->type==LBRACK) //如果当前标识符是左大括号,那么正在为一个数组的元素赋值
{
//////////////////////////////////////////////////////////
SYMLIST * tempList=new SYMLIST;
COPYLIST(tempList,listAddSym(list,BECOMES));
ARRAYELEMENT(tempList,typeItem1); //获得此数组元素的信息
delete tempList;
//////////////////////////////////////////////////////////
}
if(CurSymbol->type==BECOMES)
getASymbol();
else
{
error(7); //应该是':='
if(CurSymbol->type==EQL)
getASymbol();
}
EXPRESSION(list,typeItem2); //':='右边是表达式
if(typeItem1.typ!=typeItem2.typ)
error(37);//类型不一致
else
{
if(typeItem1.typ==ARRAYS)
{
if(typeItem1.ref==typeItem2.ref)
GEN(CPYB,0,ATAB[typeItem1.ref].size);
else
error(35);//操作数类型出错
}
else
GEN(STO,0,0);
}
}
Temporary_i=i;
}
void IFSTATEMENT(SYMLIST * list) //分析if语句
{
TYPEITEM typeItem;
int fillBackFalse,fillBackTrue;
getASymbol();
/////////////////////////////////////////////////////////////////
SYMLIST * tempList=new SYMLIST;
COPYLIST(tempList,listAddSym(listAddSym(list,DOSYM),THENSYM));
EXPRESSION(tempList,typeItem); //获取布尔表达式的信息
delete tempList;
/////////////////////////////////////////////////////////////////
if(typeItem.typ!=BOOLS)
error(32); //if或while后面的表达式类型必须为布尔类型
if(CurSymbol->type==THENSYM)
getASymbol();
else
error(11); //应该是'then'
fillBackFalse=CX; //回填
GEN(JPC,0,0);
/////////////////////////////////////////////////////////////////
SYMLIST * tempList1=new SYMLIST;
COPYLIST(tempList1,listAddSym(list,ELSESYM));
STATEMENT(tempList1); //语句分析
delete tempList1;
/////////////////////////////////////////////////////////////////
if(CurSymbol->type==ELSESYM)
{
getASymbol();
fillBackTrue=CX; //回填
GEN(JMP,0,0);
CODE[fillBackFalse].address=CX;
JUMADRTAB[JX]=CX;
JX++;
STATEMENT(list);
CODE[fillBackTrue].address=CX;
JUMADRTAB[JX]=CX;
JX++;
}
else
{
CODE[fillBackFalse].address=CX;
JUMADRTAB[JX]=CX;
JX++;
}
}
void WHILESTATEMENT(SYMLIST * list) //while 语句的分析
{
TYPEITEM typeItem;
int jumpback,fillBackFalse;
getASymbol();
JUMADRTAB[JX]=CX;
JX++;
jumpback=CX; //记录while循环执行时需要往前返回的地址
/////////////////////////////////////////////////////////////////
SYMLIST * tempList=new SYMLIST;
COPYLIST(tempList,listAddSym(list,DOSYM));
EXPRESSION(tempList,typeItem);
delete tempList;
/////////////////////////////////////////////////////////////////
if(typeItem.typ!=BOOLS)
error(32); //if或while后面的表达式类型应该是布尔类型
fillBackFalse=CX; //条件测试失败后从哪里往循环“外”跳
GEN(JPC,0,0);
if(CurSymbol->type==DOSYM)
getASymbol();
else
error(9);//应该是'do'
STATEMENT(list); //分析语句
GEN(JMP,0,jumpback);
CODE[fillBackFalse].address=CX; //回填
JUMADRTAB[JX]=CX;
JX++;
}
void COMPOUND(SYMLIST * list) //begin 开头的组合语句的分析
{
getASymbol();
////////////////////////////////////////////////////////////
SYMLIST * tempList=new SYMLIST;
COPYLIST(tempList,listAddSym(listAddSym(list,ENDSYM),SEMICOLON));
STATEMENT(tempList);
////////////////////////////////////////////////////////////
SYMLIST * tempList1=new SYMLIST;
COPYLIST(tempList1,listAddSym(&STATBEGSYS,SEMICOLON));
///////////////////////////////////////////////////////////
while(SYMINLIST(CurSymbol->type,tempList1)) //一条条的分析语句
{
if(CurSymbol->type==SEMICOLON)
getASymbol();
else
error(1);//应该是';'
STATEMENT(tempList);
}
if(CurSymbol->type==ENDSYM)
getASymbol();
else
error(12); //应该是'end'
delete tempList;delete tempList1;
}
//********************************************************* @@@@@@
void FORSTATEMENT(SYMLIST * list) //for语句分析
{
TYPEITEM typeItem;
int jumpBack,fillBackFalse;
getASymbol();
//////////////////////////////////////////////////////
SYMLIST * tempList=new SYMLIST;
COPYLIST(tempList,listAddSym(listAddSym(list,TOSYM),DOSYM));
////////////////////////////////////////////////////////////
ASSIGNMENT(list); //compile -- i:=n
int i=Temporary_i;
if(CurSymbol->type==TOSYM) //it should be "to"
getASymbol();
else
error(44);
jumpBack=CX; //jump table -- record for_begin_lab
JUMADRTAB[JX]=CX;
JX++;
GEN(LOD,NAMETAB[i].level,NAMETAB[i].unite.address);//push i to stack
EXPRESSION(list,typeItem); //compile(expression) -- m
// and push m to stack
if(typeItem.typ != INTS)
error(45); //m should be integer
GEN(LE,0,0); //compare n to m
fillBackFalse=CX; //backfill flag
GEN(JPC,0,0); //true:execute in sequence
//false:jump to for_end_lab (to be filled)
if(CurSymbol->type==DOSYM)
getASymbol();
STATEMENT(tempList); //compile statement
GEN(LODA,NAMETAB[i].level,NAMETAB[i].unite.address);//push the address of i to stack
GEN(LOD,NAMETAB[i].level,NAMETAB[i].unite.address); //push the value of i to stack
GEN(LIT,0,1); //push 1 to stack
GEN(ADD,0,0); //i
GEN(STO,0,0); //i+1 --> (i)
GEN(JMP,0,jumpBack); //jump to for_begin_lab
CODE[fillBackFalse].address=CX; //backfill for_end_lab
JUMADRTAB[JX]=CX; //jump table -- record for_end_lab
JX++;
delete tempList;
}
void REPEATSTATEMENT(SYMLIST * list) //repeat语句分析 @@@@@@
{
TYPEITEM typeItem;
int jumpback;
getASymbol(); //获取下一个符号
JUMADRTAB[JX]=CX; //将当前指令数填入跳转表 CX指令数组索引
JX++; //跳转表索引增1 JX跳转表索引
jumpback=CX; //记录repeat循环的跳转点
//*************************************************************
SYMLIST * tempList=new SYMLIST;
COPYLIST(tempList,listAddSym(list,UNTILSYM));
STATEMENT(tempList); //分析语句
//*************************************************************
if(CurSymbol->type==UNTILSYM) //应该是"until"
getASymbol();
else
error(44);
EXPRESSION(tempList,typeItem); ////获取布尔表达式的信息
delete tempList;
if(typeItem.typ!=BOOLS) //until后面的表达式类型必须为布尔类型
error(45);
GEN(JPC,0,jumpback); //产生代码: 栈顶值为0时转移至jumpback处
}
// function : compile the case statement
// annotation -- syntax of case :
// case e -- e must be integer expression or char variable
// c1 : statement
// c2 : statement
// ...
// cn : statement
// end;
// the code format:
//# recognize <case>
//# calculate expression "e"
//# jump to lab_test
//# lab1: s1 ; jump to lab_end
//# lab2: s2 ; jump to lab_end
//# ....
//# ....
//# labn: sn ; jump to lab_end
//# lab_test:
//# e == c1 ? jump to lab1 : execute in sequence
//# e == c2 ? jump to lab2 : execute in sequence
//# ...
//# e == cn ? jump to labn : execute in sequence
//# lab_end : ...
void CASESTATEMENT(SYMLIST * list)
{
TYPEITEM typeItem;
int i,needJumpTest;
IntVector PosVector; //record the position(in fact,value) of ci(c1,c2,...,cn)
IntVector L; //record the value of labi(lab1,lab2,...,labn)
IntVector NeedJumpEndVector; //record the position that need fillback lab_end
getASymbol();
FirstIn=1;
EXPRESSION(list,typeItem); //analyse "e"
i=Temporary_i; //i record position of "e" in name table
if(typeItem.typ != INTS)
error(46); //case之后的条件表达式必须是整形的结果
needJumpTest=CX; //record the code position to be fillbacked by lab_test
GEN(JMP,0,0); //jump to lab_test
while (CurSymbol->type==INTCON)
{
EXPRESSION(list,typeItem); //analyse "ci"
PosVector.push_back(Temporary_i);
L.push_back(CX);
JUMADRTAB[JX]=CX; //labi --> jump table
JX++;
if (typeItem.typ!=INTS)
error(47); //case之后的分支表达式必须是整形的结果
if (CurSymbol->type!=COLON)
error(0); //应该是 ":"
else
getASymbol();
STATEMENT(list); //analyse "si"
if (CurSymbol->type!=SEMICOLON)
error(1); //应该是";"
else
getASymbol();
NeedJumpEndVector.push_back(CX);
GEN(JMP,0,0); //jump to lab_end
}
CODE[needJumpTest].address=CX; //fillback lab_test
JUMADRTAB[JX]=CX; //lab_test --> jump table
JX++;
for(int k=0;k<L.size();k++)
{
GEN(LIT, 0,PosVector[k]);//push the value of e into stack
GEN(LOD, NAMETAB[i].level,NAMETAB[i].unite.address);//push the value of e into stack
GEN(NE,0,0); // ci != e?????
GEN(JPC,0,L[k]); // ci != e ? jump to labi : execute in sequence
}
for(k=0;k<L.size();k++)
CODE[NeedJumpEndVector[k]].address=CX; //fillback lab_end
if (CurSymbol->type!=ENDSYM)
error(12); //应该为 "end"
else
getASymbol();
}
//***********************************************************
void STANDPROC(SYMLIST * list,int i) //两个基本过程read和write的调用,他们在符号表里面分别在第六项和第七项
{
int helper;
TYPEITEM typeItem;
if(i==6)//如果是第六项,read();
{
getASymbol();
if(CurSymbol->type==LPAREN)
{
do
{
getASymbol();
if(CurSymbol->type==IDENT)
{
helper=GETPOSITION(CurSymbol->value.lpValue);
getASymbol();
if(helper==0)
{
error(33);//标识符没有定义
}
else
{
if(NAMETAB[helper].kind!=VARIABLE)
{
error(16);//应该是变量
helper=0;
}
else
{
typeItem.typ=NAMETAB[helper].type;
typeItem.ref=NAMETAB[helper].ref;
if(NAMETAB[helper].normal)
GEN(LODA,NAMETAB[helper].level,NAMETAB[helper].unite.address);
else
GEN(LOD,NAMETAB[helper].level,NAMETAB[helper].unite.address);
if(CurSymbol->type==LBRACK)
{
//////////////////////////////////////////////////////
SYMLIST * tempList1=new SYMLIST;
COPYLIST(tempList1,listAddSym(list,COMMA));
ARRAYELEMENT(tempList1,typeItem);
delete tempList1;
//////////////////////////////////////////////////////
}
if(typeItem.typ==INTS)
GEN(RED,0,0);
else if(typeItem.typ==CHARS)
GEN(RED,0,1);
else
error(35);//操作数类型错误
}
}
}
else
error(14);//应该是标识符
}while(CurSymbol->type==COMMA);
if(CurSymbol->type!=RPAREN)
{
error(2);//应该是')'
}
else
getASymbol();
}
else
error(3);//应该是'('
}
else if(i==7)//如果是第七项,write();
{
getASymbol();
if(CurSymbol->type==LPAREN)
{
do
{
getASymbol();
///////////////////////////////////////////////////////
SYMLIST * tempList=new SYMLIST;
COPYLIST(tempList,listAddSym(listAddSym(list,RPAREN),COMMA));
EXPRESSION(tempList,typeItem);
delete tempList;
////////////////////////////////////////////////////////
if(typeItem.typ==INTS)
GEN(WRT,0,0);
else if(typeItem.typ==CHARS)
GEN(WRT,0,1);
else
error(35);//操作数类型出错
}
while(CurSymbol->type==COMMA);
if(CurSymbol->type!=RPAREN)
error(2);//应该是')'
else
getASymbol();
}
else
error(3);//应该是'('
}
}
void CALL(SYMLIST * list) //调用语句的分析
{
int i,lastPar,cp,k;
TYPEITEM typeItem;
/////////////////////////////////////////////////////////////
SYMLIST * tempList=new SYMLIST;
COPYLIST(tempList,listAddSym(listAddSym(list,RPAREN),COMMA));
/////////////////////////////////////////////////////////////
getASymbol();
if(CurSymbol->type==IDENT)
{
i=GETPOSITION(CurSymbol->value.lpValue);
if(NAMETAB[i].kind==PROCEDURE)
{
if(NAMETAB[i].level==0) //如果在“过程零”,那么必定是read 或者 write
STANDPROC(list,i);
else
{
getASymbol();
GEN(OPAC,0,0);//打开活动记录
lastPar=BTAB[NAMETAB[i].ref].lastPar;
cp=i;
if(CurSymbol->type==LPAREN)
{//实在参数列表
/////////////////////////////////////////////////////////
SYMLIST * tempList1=new SYMLIST;
COPYLIST(tempList1,listAddSym(listAddSym(listAddSym(list,RPAREN),COLON),COMMA));
/////////////////////////////////////////////////////////
do
{
getASymbol();
if(cp>=lastPar)
error(28);//实参与形参个数不等
else
{
cp++;
if(NAMETAB[cp].normal)
{//值参数
EXPRESSION(tempList1,typeItem);
if(typeItem.typ==NAMETAB[cp].type)
{
if(typeItem.ref!=NAMETAB[cp].ref)
error(29);//实参与形参类型不一致
else if(typeItem.typ==ARRAYS)
GEN(LODB,0,ATAB[typeItem.ref].size);
}
else
error(29);//实参与形参类型不一致
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -