⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pl.c

📁 c 版本的pl0
💻 C
📖 第 1 页 / 共 2 页
字号:

int position(char *idt,int tx)
{
	int i;
	strcpy(table[0].name,idt);
	i=tx;
	while(strcmp(table[i].name,idt)!=0){
		i--;
	}
	return i;
}
/*
*常量声明处理
*/
int constdeclaration(int *ptx,int lev,int *pdx)
{
	if(sym==ident){
		getsymdo;
		if(sym==eql||sym==becomes){
			if(sym==becomes){
				error(1);
			}
			getsymdo;
			if(sym==number){
				enter(constant,ptx,lev,pdx);
				getsymdo;
			}
			else{
				error(2);
			}
		}
		else{
			error(3);
		}
	}
	else{
		error(4);
	}
	return 0;
}
/*
*变量声明处理
*/

int vardeclaration(int *ptx,int lev,int *pdx)
{
	if(sym==ident){
		enter(variable,ptx,lev,pdx);
		getsymdo;
	}
	else{
		error(4);
	}
	return 0;
}
/*
*输出目标代码清单
*/
void listcode(int cx0)
{
	int i;
	if(listswitch){
		for(i=cx0;i<cx;i++){
			printf("%d %s %d %d\n",i,mnemonic[code[i].f],code[i].l,code[i].a);
			fprintf(fa,"%d %s %d %d\n",i,mnemonic[code[i].f],code[i].l,code[i].a);
		}
	}
}
/*
*语句处理
*/
int statement(bool *fsys,int *ptx,int lev)
{
	int i,cxl,cx2;
	bool nxtlev[symnum];
	if(sym==ident){
		i=position(id,*ptx);
		if(i==0){
			error(11);
		}
		else{
			if(table[i].kind!=variable){
				error(12);
				i=0;
			}
			else{
				getsymdo;
				if(sym==becomes){
					getsymdo;
				}
				else{
					error(13);
				}
				memcpy(nxtlev,fsys,sizeof(bool)*symnum);
				expressiondo(nxtlev,ptx,lev);
				if(i!=0){
					gendo(sto,lev-table[i].level,table[i].adr);
				}
			}
		}//(if(i==0)
		}
	else{
		if(sym==readsym){
			getsymdo;
			if(sym!=lparen){
				error(34);
			}
			else{
				do{
					getsymdo;
					if(sym==ident){
						i=position(id,*ptx);
					}
					else{
						i=0;
					}
					if(i==0){
						error(35);
					}
					else{
						gendo(opr,0,16);
						gendo(sto,lev-table[i].level,table[i].adr);
					}
					getsymdo;
				}while(sym==comma);
			}
			if(sym!=rparen){
				error(33);
				while(!inset(sym,fsys)){
					getsymdo;
				}
			}
			else{
				getsymdo;
			}
		}
		else{
			if(sym==writesym){
				getsymdo;
				if(sym==lparen){
					do{
						getsymdo;
						memcpy(nxtlev,fsys,sizeof(bool)*symnum);
						nxtlev[rparen]=true;
						nxtlev[comma]=true;
						expressiondo(nxtlev,ptx,lev);
						gendo(opr,0,14);
					}while(sym==comma);
					if(sym!=rparen){
						error(33);
					}
					else{
						getsymdo;
					}
				}
				gendo(opr,0,15);
			}
			else{
				if(sym==callsym){
					getsymdo;
					if(sym!=ident){
						error(14);
					}
					else{
						i=position(id,*ptx);
						if(i==0){
							error(11);
						}
						else{
							if(table[i].kind==procedur){
								gendo(cal,lev-table[i].level,table[i].adr);
							}
							else{
								error(15);
							}
						}
						getsym();
					}
				}
				else{
					if(sym==ifsym){
						getsymdo;
						memcpy(nxtlev,fsys,sizeof(bool)*symnum);
						nxtlev[thensym]=true;
						nxtlev[dosym]=true;
						conditiondo(nxtlev,ptx,lev);
						if(sym==thensym){
							getsymdo;
						}
						else{
							error(16);
						}
						cxl=cx;
						gendo(jpc,0,0);
						statementdo(fsys,ptx,lev);
						code[cxl].a=cx;
					}
					else{
						if(sym==beginsym){
							getsymdo;
							memcpy(nxtlev,fsys,sizeof(bool)*symnum);
							nxtlev[semicolon]=true;
							nxtlev[endsym]=true;
							statementdo(nxtlev,ptx,lev);
							while(inset(sym,statbegsys)||sym==semicolon){
								if(sym==semicolon){
									getsymdo;
								}
								else{
									error(10);
								}
								statementdo(nxtlev,ptx,lev);
							}
							if(sym==endsym){
								getsymdo;
							}
							else{
								error(17);
							}
						}
						else{
							if(sym==whilesym){
								cxl=cx;
								getsymdo;
								memcpy(nxtlev,fsys,sizeof(bool)*symnum);
								nxtlev[dosym]=true;
								condition(nxtlev,fsys,sizeof(bool)*symnum);
								nxtlev[dosym]=true;
								conditiondo(nxtlev,ptx,lev);
								cx2=cx;
								gendo(jpc,0,0);
								if(sym==dosym){
									getsymdo;
								}
								else{
									error(18);
								}
								statementdo(fsys,ptx,lev);
								gendo(jmp,0,cxl);
								code[cx2].a=cx;
							}
							else{
								memset(nxtlev,0,sizeof(bool)*symnum);
								testdo(fsys,nxtlev,19);
							}
						}
					}
				}
			}
		}
	}
	return 0;
}
/*
*表达式处理
*/
int expression(bool *fsys,int *ptx,int lev)
{
	enum symbol addop;
	bool nxtlev[symnum];
	if(sym==plus||sym==minus){
		addop=sym;
		getsymdo;
		memcpy(nxtlev,fsys,sizeof(bool)*symnum);
		nxtlev[plus]=true;
		nxtlev[minus]=true;
		termdo(nxtlev,ptx,lev);
		if(addop==minus){
			gendo(opr,0,1);
		}
	}
	else{
		memcpy(nxtlev,fsys,sizeof(bool)*symnum);
		nxtlev[plus]=true;
		nxtlev[minus]=true;
		termdo(nxtlev,ptx,lev);
	}
	while(sym==plus||sym==minus){
		addop=sym;
		getsymdo;
		memcpy(nxtlev,fsys,sizeof(bool)*symnum);
		nxtlev[plus]=true;
		nxtlev[minus]=true;
		termdo(nxtlev,ptx,lev);
		if(addop==plus){
			gendo(opr,0,2);
		}
		else{
			gendo(opr,0,3);
		}
	}
	return 0;
}
/*
*项处理
*/
int term(bool *fsys,int *ptx,int lev)
{
	enum symbol mulop;
	bool nxtlev[symnum];
	memcpy(nxtlev,fsys,sizeof(bool)*symnum);
	nxtlev[times]=true;
	nxtlev[slash]=true;
	factordo(nxtlev,ptx,lev);
	while(sym==times||sym==slash){
		mulop=sym;
		getsymdo;
		factordo(nxtlev,ptx,lev);
		if(mulop==times){
			gendo(opr,0,4);
		}
		else{
			gendo(opr,0,5);
		}
	}
	return 0;
}
/*
*因子处理
*/
int factor(bool *fsys,int *ptx,int lev)
{
	int i;
	bool nxtlev[symnum];
	testdo(facbegsys,fsys,24);
	while(inset(sym,facbegsys)){
		if(sym==ident){
			i=position(id,*ptx);
			if(i==0){
				error(11);
			}
			else{
				switch(table[i].kind){
					case constant:
						gendo(lit,0,table[i].val);
						break;
					case variable:
						gendo(lod,lev-table[i].level,table[i].adr);
						break;
					case procedur:
						error(21);
						break;
				}
			}
			getsymdo;
		}
		else{
			if(sym==number){
				if(num>amax){
					error(31);
					num=0;
				}
				gendo(lit,0,num);
				getsymdo;
			}
			else{
				if(sym==lparen){
					getsymdo;
					memcpy(nxtlev,fsys,sizeof(bool)*symnum);
					nxtlev[rparen]=true;
					expressiondo(nxtlev,ptx,lev);
					if(sym==rparen){
						getsymdo;
					}
					else{
						error(22);
					}
				}
				testdo(fsys,facbegsys,23);
			}
		}
	}
	return 0;
}
/*
*条件处理
*/
int condition(bool *fsys,int *ptx,int lev)
{
	enum symbol relop;
	bool nxtlev[symnum];
	if(sym==oddsym){
		getsymdo;
		expressiondo(fsys,ptx,lev);
		gendo(opr,0,6);
	}
	else{
		memcpy(nxtlev,fsys,sizeof(bool)*symnum);
		nxtlev[eql]=true;
		nxtlev[neq]=true;
		nxtlev[lss]=true;
		nxtlev[leq]=true;
		nxtlev[gtr]=true;
		nxtlev[geq]=true;
		expressiondo(nxtlev,ptx,lev);
		if(sym!=eql&&sym!=neq&&sym!=lss&&sym!=leq&&sym!=gtr&&sym!=geq){
			error(20);
		}
		else{
			relop=sym;
			getsymdo;
			expressiondo(fsys,ptx,lev);
			switch(relop){
				case eql:
					gendo(opr,0,8);
					break;
				case neq:
					gendo(opr,0,9);
					break;
				case lss:
					gendo(opr,0,10);
					break;
				case geq:
					gendo(opr,0,11);
					break;
				case gtr:
					gendo(opr,0,12);
					break;
				case leq:
					gendo(opr,0,13);
					break;
			}
		}
	}
	return 0;
}
/*
*解释程序
*/
void interpret()
{
	int p,b,t;
	struct instruction i;
	int s[stacksize];
	printf("start pl0\n");
	t=0;
	b=0;
	p=0;
	s[0]=s[1]=s[2]=0;
	do{
		i=code[p];
		p++;
		switch(i.f){
			case lit:
				s[t]=i.a;
				t++;
				break;
			case opr:
				switch(i.a){
					case 0:
						t=b;
						p=s[t+2];
						b=s[t+1];
						break;
					case 1:
						s[t-1]=-s[t-1];
						break;
					case 2:
						t--;
						s[t-1]=s[t-1]+s[t];
						break;
					case 3:
						t--;
						s[t-1]=s[t-1]-s[t];
						break;
					case 4:
						t--;
						s[t-1]=s[t-1]*s[t];
						break;
					case 5:
						t--;
						s[t-1]=s[t-1]/s[t];
						break;
					case 6:
						s[t-1]=s[t-1]%2;
						break;
					case 8:
						t--;
						s[t-1]=(s[t-1]==s[t]);
						break;
					case 9:
						t--;
						s[t-1]=(s[t-1]!=s[t]);
						break;
					case 10:
						t--;
						s[t-1]=(s[t-1]<s[t]);
						break;
					case 11:
						t--;
						s[t-1]=(s[t-1]>=s[t]);
						break;
					case 12:
						t--;
						s[t-1]=(s[t-1]>s[t]);
						break;
					case 13:
						t--;
						s[t-1]=(s[t-1]<=s[t]);
						break;
					case 14:
						printf("%d",s[t-1]);
						fprintf(fa2,"%d",s[t-1]);
						t--;
						break;
					case 15:
						printf("\n");
						fprintf(fa2,"\n");
						break;
					case 16:
						printf("?");
						fprintf(fa2,"?");
						scanf("%d",&(s[t]));
						fprintf(fa2,"%d\n",s[t]);
						t++;
						break;
				}
				break;
			case lod:
				s[t]=s[base(i.l,s,b)+i.a];
				t++;
				break;
			case sto:
				t--;
				s[base(i.l,s,b)+i.a]=s[t];
				break;
			case cal:
				s[t]=base(i.l,s,b);
				s[t+1]=b;
				s[t+2]=p;
				b=t;
				p=i.a;
				break;
			case inte:
				t+=i.a;
				break;
			case jmp:
				p=i.a;
				break;
			case jpc:
				t--;
				if(s[t]==0){
					p=i.a;
				}
				break;
			}
		}while(p!=0);
}
/*
通过过程基址求上1层过程的基址
*/
int base(int l,int *s,int b)
{
	int bl;
	bl=b;
	while(l>0){
		bl=s[b];
		l--;
	}
	return bl;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -