?? yy.cpp
字號:
#include "cifa.h"
#include "iostream.h"
#include "stdlib.h"
# define FALSE false
# define TRUE true
//FILE *fp1;
//fp1=fopen("sour.txt","r");
cifa c1(fopen("sour.txt","r"));
int qiantao=0;//錢掏變量
struct errorType
{
int ErrorNumber;//語法語義錯誤代碼
int ErrorAddress;//語義錯誤對應二元式的地址
};
struct yujutype
{
int Etyp;
int Evalue;
int TC;
int FC;
int Code;
};
struct idtype //標識符表
{
char name[20];//名字
int typ;//類型1:integer,2:real,3:program or procedure name
int kind;//屬性1:簡單變量,2:臨時變量,3:值參變量,4:變參變量
int addr;//地址
};
struct leveltype //層次表
{
char name[20];//名字
int outern;//外層
int lnum;//層次號
int parnum;//參數個數
int varnum;//變量個數
int pointer;//標識符表首址
int recl;//活動記錄長度
int temp;//臨時變量首址
int lnp;//入口
};
struct temptype //
{
bool used;//
int typ;//
int taddr;//
};
struct argtype //
{
int fl;//類型1:常數2:指令入口3:臨時變量4:直接訪問變量5:間接訪問變量6+i:第i外層變量
int flvalue;//值 常數值|指令地址|相對地址
};
struct quadtype //四元式表
{
int op;//操作
argtype arg1;//操作數
argtype arg2;//操作數
argtype result;//結果
};
struct quanjutype //變量
{
int lasent;//標識符表長度指針
int lastbl;//層次表長度指針
int currbl;//當前層指針
int tempp;//變量表藏度指針
int nxq;//四元式表長度指針
};
errorType errorvalue;
yujutype yujuvalue;
CifaResult yy_tCifa[500];
char yy_QuadOpCodeTable[30][10];
char yy_tErrorMessage[100][30];
int yy_pCurSym=0;
void coutgen();
void coutty();
int merge(int,int,int);
int newtemp(int);
int lookupp(char *);
int lookupv_onelevel(char *,int);
void backpatch(int,int,int,int);
void addid(char *,int,int,int);
quanjutype quanjuvalue;
void gen(char *,int,int,int,int,int,int);
idtype idtab[10000];
leveltype leveltab[100];
temptype temptab[100];
quadtype quad[10000];
int yy_nErrorAddress;
int yy_nErrorNum;
CifaResult GetNextSym();
void NextSym();
CifaResult GetCurSym();
void initial();
int s_GuanXi();
int s_GuanXiBiaoDaShi();
int s_BuErBiaoDaShi();
int s_YingZi();
int s_Xiang();
int s_BiaoDaShi();
int s_XunHuanYuJu();
int s_TiaoJianYuJu();
int s_FuZhiYuJu();
int s_FuHeYuJu();
int s_YuJu();
int s_YuJuChuan();
int s_XingChan();
int s_XingChanBuFeng();
int s_JianBianShuoMing();
int s_ShuoMing();
int s_ShuoMingChuan();
int s_ChengXuTi();
int s_ChengXu();
void gen(char * op,int a1,int a2,int a3,int a4,int a5,int a6)
{
if (quanjuvalue.nxq>=1000-1) return;
int r=29;
for (int i=0;i<1000;i++)
{
if (!stricmp(yy_QuadOpCodeTable[i],op))
{
r=i;break;
}
}
quad[quanjuvalue.nxq].op=r;
quad[quanjuvalue.nxq].arg1.fl=a1;
quad[quanjuvalue.nxq].arg1.flvalue=a2;
quad[quanjuvalue.nxq].arg2.fl=a3;
quad[quanjuvalue.nxq].arg2.flvalue=a4;
quad[quanjuvalue.nxq].result.fl=a5;
quad[quanjuvalue.nxq].result.flvalue=a6;
quanjuvalue.nxq++;
}
void addid(char * name, int typ, int kind, int addr)
{
if (quanjuvalue.lasent>=1000-1) return;
::strcpy(idtab[quanjuvalue.lasent].name,name);
idtab[quanjuvalue.lasent].typ=typ;
idtab[quanjuvalue.lasent].kind=kind;
idtab[quanjuvalue.lasent].addr=addr;
quanjuvalue.lasent++;
}
void backpatch(int link, int point, int v1, int v2)
{
if (link==0) return;
switch (point)
{
case 2:
backpatch(quad[link].arg1.fl,point,v1,v2);
quad[link].arg1.fl=v1;
quad[link].arg1.flvalue=v2;
break;
case 3:
backpatch(quad[link].arg2.fl,point,v1,v2);
quad[link].arg2.fl=v1;
quad[link].arg2.flvalue=v2;
break;
case 4:
backpatch(quad[link].result.fl,point,v1,v2);
quad[link].result.fl=v1;
quad[link].result.flvalue=v2;
break;
default:
return;
}
}
int lookupp(char * id)
{
for (int i=0;i<quanjuvalue.lastbl;i++)
if (!::stricmp(id,leveltab[i].name)) return i;
return -1;
}
int lookupv_onelevel(char * idname, int idlevel)//
{
if (!::stricmp(idname,leveltab[idlevel].name)) return -1;
int n=leveltab[idlevel].varnum+leveltab[idlevel].parnum;
int pointer=leveltab[idlevel].pointer;
for (int i=pointer;i<(pointer+n);i++)
if (!::stricmp(idname,idtab[i].name)) return i;
return 0;
}
int lookupv_alllevel(char * name, int & level)
{
int i=level;
int r;
while(1)
{
if (i<0) return 0;
r=lookupv_onelevel(name,i);
switch (r)
{
case -1:
level=i;
return -1;
case 0:
i--;
break;
default:
level=i;
return r;
}
}
}
CifaResult GetCurSym()
{
return yy_tCifa[yy_pCurSym];
}
void NextSym()
{
yy_pCurSym++;
}
CifaResult GetNextSym()
{
return yy_tCifa[yy_pCurSym+1];
}
int YuYiFengXi()
{
quanjuvalue.currbl=0;
quanjuvalue.lasent=0;
quanjuvalue.lastbl=0;
quanjuvalue.nxq=0;
quanjuvalue.tempp=0;
gen("",0,0,0,0,0,0);//idtab start from 1
addid("",0,0,0);//idtab start from 1
yy_pCurSym=0;
if(!s_ChengXu()) return FALSE;
gen("_End_",0,0,0,0,0,0);//end note
return 1;
}
int s_ChengXu()
{
switch (GetCurSym().type)
{
case 3://program
break;
default:
yy_nErrorNum=3;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
switch (GetCurSym().type)
{
case 1://id
break;
default:
yy_nErrorNum=4;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
//yy
//對層次的副直
leveltab[quanjuvalue.currbl].lnp=quanjuvalue.nxq+1;
//cout<<"fasdfas亂七八糟 "<<leveltab[quanjuvalue.currbl].lnp<<endl;
leveltab[quanjuvalue.currbl].lnum=0;
strcpy(leveltab[quanjuvalue.currbl].name,GetCurSym().text);
leveltab[quanjuvalue.currbl].outern=0;
leveltab[quanjuvalue.currbl].parnum=0;
leveltab[quanjuvalue.currbl].pointer=quanjuvalue.lasent;
leveltab[quanjuvalue.currbl].recl=5;
leveltab[quanjuvalue.currbl].varnum=0;
leveltab[quanjuvalue.currbl].temp=quanjuvalue.tempp;
quanjuvalue.lastbl++;
gen("call",1,0,1,0,2,2);
int link=quanjuvalue.nxq;
gen("in",0,0,0,0,0,0);
//yy end
NextSym();
switch (GetCurSym().type)
{
case 30://;
break;
default:
yy_nErrorNum=5;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
if (!s_ChengXuTi()) return FALSE;
//yy
// printf("餓我我哦我外哦我哦我我忘我歐文\n");
backpatch(link,2,2,leveltab[quanjuvalue.currbl].recl);
gen("out",0,0,0,0,0,0);
gen("ret",0,0,0,0,0,0);
quanjuvalue.currbl=leveltab[quanjuvalue.currbl].outern;
quanjuvalue.tempp=leveltab[quanjuvalue.currbl].temp;
//yy end
switch (GetCurSym().type)
{
case 31://.
break;
default:
yy_nErrorNum=6;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
return TRUE;
}
int s_ChengXuTi()
{
switch (GetCurSym().type)
{
case 14://integer
case 15://real
// case 5://procedure程序不要過程
if (!s_ShuoMingChuan()) return FALSE;
switch (GetCurSym().type)
{
case 30://;
break;
default:
yy_nErrorNum=5;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
break;
case 6://begin
break;
default:
yy_nErrorNum=7;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
switch (GetCurSym().type)
{
case 6://begin
break;
default:
yy_nErrorNum=8;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
if (!s_YuJuChuan()) return FALSE;
//cout<<"我愛我愛我愛我愛"<<endl;
switch (GetCurSym().type)
{
case 7://end
break;
default:
yy_nErrorNum=10;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
return TRUE;
}
int s_ShuoMingChuan()
{
if (!s_ShuoMing()) return FALSE;
while (GetCurSym().type==30
&& GetNextSym().type!=6)//; begin
{
NextSym();
if (!s_ShuoMing()) return FALSE;
}
return TRUE;
}
int s_ShuoMing()
{
switch (GetCurSym().type)
{
case 14://integer
case 15://real
if (!s_JianBianShuoMing()) return FALSE;
break;
//case 5://procedure
//if (!s_GuoChengShuoMing()) return FALSE;
// break;
default:
yy_nErrorNum=11;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
return TRUE;
}
int s_JianBianShuoMing()
{
int typ;//yy
switch (GetCurSym().type)
{
case 14://integer
typ=1;//yy
break;
case 15://real
typ=2;//yy
break;
default:
yy_nErrorNum=12;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
switch (GetCurSym().type)
{
case 1://id
break;
default:
yy_nErrorNum=14;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
//yy
switch (lookupv_onelevel(GetCurSym().text,quanjuvalue.currbl))
{
case -1:
yy_nErrorNum=31;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
case 0:
addid(GetCurSym().text,typ,1,leveltab[quanjuvalue.currbl].recl);
leveltab[quanjuvalue.currbl].varnum++;
leveltab[quanjuvalue.currbl].recl+=typ;
break;
default:
yy_nErrorNum=32;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
//yy end
NextSym();
while (GetCurSym().type==32) //,
{
NextSym();
switch (GetCurSym().type)
{
case 1://id
break;
default:
yy_nErrorNum=14;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
//yy
switch (lookupv_onelevel(GetCurSym().text,quanjuvalue.currbl))
{
case -1:
yy_nErrorNum=31;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
case 0:
addid(GetCurSym().text,typ,1,leveltab[quanjuvalue.currbl].recl);
leveltab[quanjuvalue.currbl].varnum++;
leveltab[quanjuvalue.currbl].recl+=typ;
break;
default:
yy_nErrorNum=32;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
//yy end
NextSym();
}
return TRUE;
}
int s_YuJuChuan()
{
if (!s_YuJu()) return FALSE;
while (GetCurSym().type==30)//;
{
NextSym();
if (!s_YuJu()) return FALSE;
}
cout<<"語句串結束"<<endl;
return TRUE;
}
int s_YuJu()
{
switch (GetCurSym().type)
{
case 6://begin
if (!s_FuHeYuJu()) return FALSE;
break;
case 1://id
if (!s_FuZhiYuJu()) return FALSE;
break;
case 8://if
if (!s_TiaoJianYuJu()) return FALSE;
break;
case 11://while
if (!s_XunHuanYuJu()) return FALSE;
break;
// case 13://call
// if (!s_GuoChengYuJu()) return FALSE;
// break;
default:
yy_nErrorNum=9;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
return TRUE;
}
int s_FuHeYuJu()
{
switch (GetCurSym().type)
{
case 6://begin
break;
default:
yy_nErrorNum=8;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
if (!s_YuJuChuan()) return FALSE;
switch (GetCurSym().type)
{
case 7://end
break;
default:
yy_nErrorNum=10;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
return TRUE;
}
int s_FuZhiYuJu()
{
switch (GetCurSym().type)
{
case 1://id
break;
default:
yy_nErrorNum=20;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
//yy
int idlevel=quanjuvalue.currbl;
int idpoint=lookupv_alllevel(GetCurSym().text,idlevel);
if (idpoint==0)
{
yy_nErrorNum=33;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
if (idpoint==-1)
{
yy_nErrorNum=34;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
int t1=idtab[idpoint].typ;
int k1=idtab[idpoint].addr;
int i1;
if (idlevel==quanjuvalue.currbl)
{
if (idtab[idpoint].kind==4) i1=5;
else i1=4;
}
else
{
i1=idlevel+6;
}
//yy end
NextSym();
switch (GetCurSym().type)
{
case 29://:=
break;
default:
yy_nErrorNum=21;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
if (!s_BiaoDaShi()) return FALSE;
//yy
int t2;
int k2;
int i2=yujuvalue.Etyp;
int j2=yujuvalue.Evalue;
if (i2==1)
{
k2=j2;
t2=1;
}
else if (i2==2)
{
k2=temptab[j2].taddr;
t2=temptab[j2].typ;
i2=3;
}
else
{
k2=idtab[j2].addr;
t2=idtab[j2].typ;
i2+=1;
}
if (t1<t2)
{
yy_nErrorNum=35;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
if (t1==1) gen(":=I",i1,k1,i2,k2,0,0);
else gen(":=R",i1,k1,i2,k2,0,0);
if (i2==3) temptab[j2].used=FALSE;
//yy end
return TRUE;
}
int s_TiaoJianYuJu()
{
switch (GetCurSym().type)
{
case 8://if
break;
default:
yy_nErrorNum=22;
yy_nErrorAddress=yy_pCurSym;
return FALSE;
}
NextSym();
if (!s_BuErBiaoDaShi()) return FALSE;
//yy
int TCexit=yujuvalue.TC;
int FCexit=yujuvalue.FC;
backpatch(TCexit,4,2,quanjuvalue.nxq);
// cout<<"if語句的真出口"<<quanjuvalue.nxq<<endl;
//yy end
switch (GetCurSym().type)
{
case 9://then
break;
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -