版權(quán)說(shuō)明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)
文檔簡(jiǎn)介
1、<p> 《編譯原理課程設(shè)計(jì)》</p><p> 項(xiàng)目名稱 PL/0語(yǔ)言的擴(kuò)充 </p><p> 學(xué) 院 計(jì)算機(jī)學(xué)院 </p><p><b> 專業(yè)班級(jí) </b></p><p> 學(xué) 號(hào) </p>
2、<p> 姓 名 </p><p> 指導(dǎo)教師 </p><p> 2013 年 1 月 3 日</p><p> 一. 課程設(shè)計(jì)目的0</p><p> 二. 課程設(shè)計(jì)要求0</p><p><b>
3、; 基本內(nèi)容:0</b></p><p><b> 選做內(nèi)容:0</b></p><p><b> 已實(shí)現(xiàn)的功能:0</b></p><p> 三. 編譯環(huán)境與工具0</p><p> 四. 結(jié)構(gòu)設(shè)計(jì)說(shuō)明0</p><p> 1.PL/0編譯
4、程序的結(jié)構(gòu)圖0</p><p> 2.PL/0編譯程序的過(guò)程或函數(shù)的功能表1</p><p> 3.PL/0編譯程序的總體流程圖1</p><p> 4.PL/0編譯程序的中間代碼2</p><p> 5.PL\0的編譯程序的過(guò)程和函數(shù)的功能3</p><p> 五. 課程設(shè)計(jì)的設(shè)計(jì)與步驟3<
5、;/p><p> 1.?dāng)U充賦值運(yùn)算:+= -= *= /= ++ 和- -5</p><p> 2.增加Pascal的FOR語(yǔ)句15</p><p><b> 3.一維數(shù)組17</b></p><p> 六. 調(diào)試測(cè)試19</p><p> 1.+= -= *= /= ++ --
6、的測(cè)試19</p><p> 2.FOR語(yǔ)句的測(cè)試21</p><p> 3.數(shù)組的調(diào)試22</p><p><b> 4.綜合調(diào)試23</b></p><p> 七. 課程設(shè)計(jì)總結(jié)25</p><p><b> 【參考文獻(xiàn)】26</b></p&g
7、t;<p><b> 課程設(shè)計(jì)目的</b></p><p> 在分析理解一個(gè)教學(xué)型編譯程序(如PL/0)的基礎(chǔ)上,對(duì)其詞法分析程序、語(yǔ)法分析程序和語(yǔ)義處理程序進(jìn)行部分修改擴(kuò)充。達(dá)到進(jìn)一步了解程序編譯過(guò)程的基本原理和基本實(shí)現(xiàn)方法的目的。</p><p><b> 課程設(shè)計(jì)要求</b></p><p>&l
8、t;b> 基本內(nèi)容:</b></p><p> (1)擴(kuò)充賦值運(yùn)算:*= 和 /=</p><p> ?。?)擴(kuò)充語(yǔ)句(Pascal的FOR語(yǔ)句):</p><p> ?、貴OR <變量>:=<表達(dá)式> TO <表達(dá)式> DO <語(yǔ)句></p><p> ②FOR <
9、;變量>:=<表達(dá)式> DOWNTO <表達(dá)式> DO <語(yǔ)句></p><p> 其中,語(yǔ)句①的循環(huán)變量的步長(zhǎng)為2,語(yǔ)句②的循環(huán)變量的步長(zhǎng)為-2。</p><p> ?。?)增加運(yùn)算:++ 和 --。</p><p><b> 選做內(nèi)容:</b></p><p> ?。?)
10、增加類型:① 字符類型;② 實(shí)數(shù)類型。</p><p> ?。?)擴(kuò)充函數(shù):① 有返回值和返回語(yǔ)句;② 有參數(shù)函數(shù)。</p><p> ?。?)增加一維數(shù)組類型(可增加指令)。</p><p> ?。?)其他典型語(yǔ)言設(shè)施。</p><p><b> 已實(shí)現(xiàn)的功能:</b></p><p> (
11、1)擴(kuò)充賦值運(yùn)算:*=和 /= (另外也擴(kuò)充了+= 和 -=)</p><p> ?。?)擴(kuò)充語(yǔ)句(Pascal的FOR語(yǔ)句):</p><p> ?、貴OR <變量>:=<表達(dá)式> TO <表達(dá)式> DO <語(yǔ)句></p><p> ?、贔OR <變量>:=<表達(dá)式> DOWNTO <表
12、達(dá)式> DO <語(yǔ)句></p><p> (3)增加運(yùn)算:++ 和 --。</p><p> (4)增加一維數(shù)組類型(可增加指令)。</p><p><b> 編譯環(huán)境與工具</b></p><p> 編譯環(huán)境:Microsoft Windows 7 (64bit)</p><
13、;p> 編譯工具:Microsoft Visual C++ 6.0</p><p><b> 結(jié)構(gòu)設(shè)計(jì)說(shuō)明</b></p><p> 1.PL/0編譯程序的結(jié)構(gòu)圖</p><p> 2.PL/0編譯程序的過(guò)程或函數(shù)的功能表</p><p> 表4-1 PL/0編譯程序的過(guò)程或函數(shù)的功能表</p&g
14、t;<p> 3.PL/0編譯程序的總體流程圖</p><p> 圖4-2 PL/0編譯程序的總體流程圖</p><p> 4.PL/0編譯程序的中間代碼</p><p> 對(duì)PL/0編譯程序的目標(biāo)代碼的指令格式描述如下:</p><p> f l a</p>
15、<p> 其中f代表功能碼,l表示層次差,a的含意對(duì)不同的指令有所區(qū)別,見(jiàn)下面對(duì)每條指令的解釋說(shuō)明:</p><p> 表4-2 PL/0編譯程序的目標(biāo)指令</p><p> 5.PL\0的編譯程序的過(guò)程和函數(shù)的功能</p><p><b> Pl0:主程序</b></p><p> Error:出
16、錯(cuò)處理,打印出錯(cuò)位置和錯(cuò)誤編碼</p><p> Getsym:詞法分析,讀取一個(gè)單詞</p><p> Getch:漏掉空格,讀取一個(gè)字符</p><p> Gen:生成目標(biāo)代碼,并送入目標(biāo)程序區(qū)</p><p> Test:測(cè)試當(dāng)前單詞符號(hào)是否合法</p><p> Block:分程序分析處理過(guò)程<
17、/p><p> Enter:登陸名字表</p><p> Position:查找標(biāo)識(shí)符在名字表中的位置</p><p> Constdeclaration:常量定義處理</p><p> Vardeclaration:變量說(shuō)明處理</p><p> Listcode:列出目標(biāo)代碼清單</p><
18、;p> Statement:語(yǔ)句部分處理</p><p> Expression:表達(dá)式處理</p><p><b> Term:項(xiàng)處理</b></p><p> Factor:因子處理</p><p> Condition:條件處理</p><p> Interpret:對(duì)目標(biāo)
19、代碼的解釋執(zhí)行程序</p><p> Base:通過(guò)靜態(tài)鏈求出數(shù)據(jù)區(qū)的基地址</p><p> 課程設(shè)計(jì)的設(shè)計(jì)與步驟</p><p> 本次課程設(shè)計(jì)是在實(shí)驗(yàn)的基礎(chǔ)上,在實(shí)驗(yàn)中,已經(jīng)實(shí)現(xiàn)對(duì)PL/0作以下修改擴(kuò)充:</p><p> ?。?)增加單詞:保留字 ELSE,F(xiàn)OR,STEP,UNTIL,RETURN </p>&l
20、t;p> 運(yùn)算符 +=,-=,++,--,∧,∨,┓</p><p> ?。?)修改單詞:不等號(hào)# 改為 <></p><p> ?。?)增加條件語(yǔ)句的ELSE子句</p><p> 在課程設(shè)計(jì)中,因?yàn)殛P(guān)鍵字增加到了18個(gè),所以令 # define norw 18。SYMBOL擴(kuò)展為48個(gè)值。在pl0.h中做了如下更改,具體如下(粗體部分為課程
21、設(shè)計(jì)更改部分):</p><p> enum symbol{</p><p> nul, ident, number, plus, minus,</p><p> times, slash, oddsym, eql, neq,</p><p> lss, leq, g
22、tr, geq, lparen,</p><p> rparen, comma, semicolon,period, becomes,</p><p> beginsym, endsym, ifsym, thensym, whilesym,</p><p> writesym, readsym, dosym, callsym
23、, constsym,</p><p> varsym, procsym, elsesym, forsym, stepsym, untilsym, returnsym,</p><p> plusbecomes, dplus, minusbecomes, dminus, and, or, not,lepa,ripa,</p><p> slashbecom
24、es,timesbecomes,</p><p><b> };</b></p><p> #define symnum 48 </p><p> 符號(hào)和關(guān)鍵字?jǐn)U展(粗體部分為課程設(shè)計(jì)更改部分):</p><p> ssym['+']=plus;</p><p> ssy
25、m['-']=minus;</p><p> ssym['*']=times;</p><p> ssym['/']=slash;</p><p> ssym['(']=lparen;</p><p> ssym[')']=rparen;</p>
26、;<p> ssym['=']=eql;</p><p> ssym[',']=comma;</p><p> ssym['.']=period;</p><p> //ssym['#']=neq; 去掉#,改為<></p><p> ssym
27、[';']=semicolon;</p><p> ssym['!']=not; //非</p><p> ssym['[']=lepa;//一維數(shù)組的左括號(hào)[</p><p> ssym[']']=ripa;//一維數(shù)組的右括號(hào)]</p><p> /*設(shè)置保留字名字
28、,按照字母順序,便于折半查找*/</p><p> strcpy(&(word[0][0]),"begin");</p><p> strcpy(&(word[1][0]),"call");</p><p> strcpy(&(word[2][0]),"const");<
29、/p><p> strcpy(&(word[3][0]),"do");</p><p> strcpy(&(word[4][0]),"else");</p><p> strcpy(&(word[5][0]),"end");</p><p> strcpy
30、(&(word[6][0]),"for");</p><p> strcpy(&(word[7][0]),"if");</p><p> strcpy(&(word[8][0]),"odd");</p><p> strcpy(&(word[9][0]),"p
31、rocedure");</p><p> strcpy(&(word[10][0]),"read");</p><p> strcpy(&(word[11][0]),"return");</p><p> strcpy(&(word[12][0]),"step");&
32、lt;/p><p> strcpy(&(word[13][0]),"then");</p><p> strcpy(&(word[14][0]),"until");</p><p> strcpy(&(word[15][0]),"var");</p><p>
33、; strcpy(&(word[16][0]),"while");</p><p> strcpy(&(word[17][0]),"write");</p><p> /*設(shè)置保留字符號(hào)*/</p><p> wsym[0]=beginsym;</p><p> wsym[1]
34、=callsym;</p><p> wsym[2]=constsym;</p><p> wsym[3]=dosym;</p><p> wsym[4]=elsesym;</p><p> wsym[5]=endsym;</p><p> wsym[6]=forsym;</p><p&g
35、t; wsym[7]=ifsym;</p><p> wsym[8]=oddsym;</p><p> wsym[9]=procsym;</p><p> wsym[10]=readsym;</p><p> wsym[11]=returnsym; </p><p> wsym[12]=stepsym;&l
36、t;/p><p> wsym[13]=thensym;</p><p> wsym[14]=untilsym;</p><p> wsym[15]=varsym;</p><p> wsym[16]=whilesym;</p><p> wsym[17]=writesym;</p><p>
37、; 設(shè)置指令名稱(粗體部分為課程設(shè)計(jì)更改部分):</p><p> strcpy(&(mnemonic[lit][0]),"lit");</p><p> strcpy(&(mnemonic[opr][0]),"opr");</p><p> strcpy(&(mnemonic[lod][0])
38、,"lod");</p><p> strcpy(&(mnemonic[sto][0]),"sto");</p><p> strcpy(&(mnemonic[cal][0]),"cal");</p><p> strcpy(&(mnemonic[inte][0]),"
39、;int");</p><p> strcpy(&(mnemonic[jmp][0]),"jmp");</p><p> strcpy(&(mnemonic[jpc][0]),"jpc");</p><p> strcpy(&(mnemonic[gar][0]),"gar&qu
40、ot;);</p><p> strcpy(&(mnemonic[sar][0]),"sar");</p><p> strcpy(&(mnemonic[shd][0]),"shd");</p><p> strcpy(&(mnemonic[del][0]),"del");&l
41、t;/p><p> strcpy(&(mnemonic[jud][0]),"jud");</p><p> strcpy(&(mnemonic[tra][0]),"tra");</p><p> 1.?dāng)U充賦值運(yùn)算:+= -= *= /= ++ 和- -</p><p> 1)在s
42、ymbol增加字符:</p><p> Plusbecomes:+=</p><p> Minusbecomes:-=</p><p> Slashbecomes:*=</p><p> Timesbecomes:/=</p><p> 2)對(duì)取字符getsym()函數(shù)進(jìn)行擴(kuò)充,具體如下(粗體部分為更改部分)
43、:</p><p> int getsym()</p><p><b> {</b></p><p> ...//此處省略部分未修改過(guò)的代碼</p><p> else if(ch=='+') //讀到加號(hào)</p><p><b> {</b>&l
44、t;/p><p> getchdo; //再讀一個(gè)字符</p><p> if(ch=='=') //讀到等號(hào),則與+號(hào)構(gòu)成加等</p><p><b> {</b></p><p> sym=plusbecomes;</p><p><b> getchdo;&
45、lt;/b></p><p><b> }</b></p><p> else if(ch=='+') //讀到加號(hào),則與加號(hào)構(gòu)成++</p><p><b> {</b></p><p> sym=dplus;</p><p> getchd
46、o; </p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><p> sym=plus; //那就是一個(gè)單獨(dú)的加號(hào)</p><p><b> }</b
47、></p><p><b> }</b></p><p> else if(ch=='-') //讀到減號(hào)</p><p><b> {</b></p><p><b> getchdo;</b></p><p> if
48、(ch=='=') //讀到等號(hào),則與減號(hào)構(gòu)成減等</p><p><b> {</b></p><p> sym=minusbecomes;</p><p><b> getchdo;</b></p><p><b> }</b></p>
49、;<p> else if(ch=='-') //讀到減號(hào),則與減號(hào)構(gòu)成--</p><p><b> {</b></p><p> sym=dminus;</p><p><b> getchdo;</b></p><p><b> }</
50、b></p><p><b> else</b></p><p><b> {</b></p><p> sym=minus; //那就是一個(gè)單獨(dú)的減號(hào)</p><p><b> }</b></p><p><b> }<
51、/b></p><p> else if(ch=='*') </p><p><b> {</b></p><p><b> getchdo;</b></p><p> if(ch=='=') //讀到乘號(hào),則與減號(hào)構(gòu)成乘等</p>&
52、lt;p><b> {</b></p><p> sym=timesbecomes;</p><p><b> getchdo;</b></p><p><b> }</b></p><p><b> else</b></p>
53、<p><b> {</b></p><p> sym=times; //那就是一個(gè)單獨(dú)的乘</p><p><b> }</b></p><p><b> }</b></p><p> else if(ch=='/') </p>
54、;<p><b> {</b></p><p><b> getchdo;</b></p><p> if(ch=='=') //讀到乘號(hào),則與減號(hào)構(gòu)成除等</p><p><b> {</b></p><p> sym=slashb
55、ecomes;</p><p><b> getchdo;</b></p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><p> sym=slas
56、h; //那就是一個(gè)單獨(dú)的除</p><p><b> }</b></p><p><b> }</b></p><p> ...//此處省略部分未修改過(guò)的代碼</p><p><b> }</b></p><p> 3)對(duì)statemen函數(shù)
57、進(jìn)行擴(kuò)展</p><p> int statement(bool* fsys,int * ptx,int lev)</p><p><b> {</b></p><p> ...//此處省略部分未修改過(guò)的代碼</p><p> if(sym==ident)</p><p><b>
58、; {</b></p><p> i=position(id,*ptx);</p><p><b> if(i==0)</b></p><p><b> {</b></p><p> error(11);</p><p><b> }<
59、/b></p><p><b> else</b></p><p><b> {</b></p><p> if(table[i].kind!=variable&&table[i].kind!=array)</p><p><b> {</b>&l
60、t;/p><p> error(12);</p><p><b> i=0;</b></p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p>
61、<p><b> getsymdo;</b></p><p> if(sym==lepa)//如果是數(shù)組</p><p><b> {</b></p><p> getsymdo; //處理[]里的表達(dá)式</p><p> memcpy(nxtlev,fsys,sizeof(b
62、ool)* symnum);</p><p> nxtlev[ripa]=true;</p><p> expressiondo(nxtlev,ptx,lev);</p><p> gendo(tra,0,table[i].size);//生成將數(shù)組下標(biāo)范圍入棧指令</p><p> gendo(jud,0,0);//判斷下標(biāo)合法性&
63、lt;/p><p> if(sym!=ripa)</p><p><b> {</b></p><p> error(26);</p><p><b> }</b></p><p><b> getsymdo;</b></p><
64、;p><b> }</b></p><p> if(sym==becomes)//賦值:=</p><p><b> {</b></p><p><b> getsymdo;</b></p><p><b> flag=1;</b><
65、/p><p><b> }</b></p><p> else if(sym==plusbecomes)//加賦值+=</p><p><b> {</b></p><p><b> getsymdo;</b></p><p><b>
66、flag=2;</b></p><p><b> }</b></p><p> else if(sym==minusbecomes)//減賦值-=</p><p><b> {</b></p><p><b> getsymdo;</b></p>
67、<p><b> flag=3;</b></p><p><b> }</b></p><p> else if(sym==dplus)//++</p><p><b> {</b></p><p><b> getsymdo;</b&g
68、t;</p><p><b> flag=4;</b></p><p><b> }</b></p><p> else if(sym==dminus)//--</p><p><b> {</b></p><p><b> gets
69、ymdo;</b></p><p><b> flag=5;</b></p><p><b> }</b></p><p> else if(sym==timesbecomes)//*=</p><p><b> {</b></p><p
70、><b> getsymdo;</b></p><p><b> flag=6;</b></p><p><b> }</b></p><p> else if(sym==slashbecomes)// /=</p><p><b> {</b&
71、gt;</p><p><b> getsymdo;</b></p><p><b> flag=7;</b></p><p><b> }</b></p><p><b> else</b></p><p><b&g
72、t; {</b></p><p> error(13);</p><p><b> }</b></p><p><b> if(i!=0)</b></p><p><b> {</b></p><p> if(flag==1) /
73、/:=</p><p><b> {</b></p><p> memcpy(nxtlev,fsys,sizeof(bool)* symnum);</p><p> expressiondo(nxtlev,ptx,lev);</p><p><b> }</b></p><
74、;p> else if(flag==2)//+=</p><p><b> {</b></p><p> memcpy(nxtlev,fsys,sizeof(bool)* symnum);</p><p> expressiondo(nxtlev,ptx,lev);</p><p> gendo(lod,
75、lev-table[i].level,table[i].adr);//先取值到棧頂</p><p> gendo(opr,lev-table[i].level,2);//執(zhí)行加法</p><p><b> }</b></p><p> else if(i!=0&&flag==3)//-=</p><p&
76、gt;<b> {</b></p><p> memcpy(nxtlev,fsys,sizeof(bool)* symnum);</p><p> expressiondo(nxtlev,ptx,lev);</p><p> gendo(lod,lev-table[i].level,table[i].adr);//先取值到棧頂</
77、p><p> gendo(opr,lev-table[i].level,3);//執(zhí)行減法</p><p> gendo(opr,lev-table[i].level,1);//取反</p><p><b> }</b></p><p> else if(i!=0&&flag==4) //++<
78、/p><p><b> {</b></p><p> if(table[i].kind==variable)</p><p><b> {</b></p><p> gendo(lod,lev-table[i].level,table[i].adr);//先取值到棧頂</p>&l
79、t;p> gendo(lit,lev-table[i].level,1);//將值為1入棧</p><p> gendo(opr,lev-table[i].level,2);//加法,即加1</p><p><b> }</b></p><p> if(table[i].kind==array)</p><p&
80、gt;<b> {</b></p><p> gendo(gar,lev-table[i].level,table[i].adr);</p><p> gendo(lit,lev-table[i].level,1);</p><p> gendo(opr,lev-table[i].level,2);</p><p&g
81、t;<b> }</b></p><p><b> }</b></p><p> else if(i!=0&&flag==5)//--</p><p><b> {</b></p><p> if(table[i].kind==variable)<
82、;/p><p><b> {</b></p><p> gendo(lod,lev-table[i].level,table[i].adr);//先取值到棧頂</p><p> gendo(lit,lev-table[i].level,1);//將值為1入棧</p><p> gendo(opr,lev-table[
83、i].level,3);//減法,即-1</p><p><b> }</b></p><p> if(table[i].kind==array)</p><p><b> {</b></p><p> gendo(gar,lev-table[i].level,table[i].adr);&
84、lt;/p><p> gendo(lit,lev-table[i].level,1);</p><p> gendo(opr,lev-table[i].level,3);</p><p><b> }</b></p><p><b> }</b></p><p> el
85、se if(i!=0&&flag==6)//*=</p><p><b> {</b></p><p> memcpy(nxtlev,fsys,sizeof(bool)* symnum);</p><p> expressiondo(nxtlev,ptx,lev);</p><p> gendo(
86、lod,lev-table[i].level,table[i].adr);//先取值到棧頂</p><p> gendo(opr,lev-table[i].level,4);//乘法</p><p><b> }</b></p><p> else if(i!=0&&flag==7) // /=;</p>&
87、lt;p><b> {</b></p><p> gendo(lod,lev-table[i].level,table[i].adr);//先取值到棧頂</p><p> memcpy(nxtlev,fsys,sizeof(bool)* symnum);</p><p> expressiondo(nxtlev,ptx,lev);
88、</p><p> gendo(opr,lev-table[i].level,5);//除法</p><p><b> }</b></p><p> if(table[i].kind==array) //數(shù)組,根據(jù)偏移地址存入數(shù)組</p><p><b> {</b></p>
89、<p> gendo(sar,lev-table[i].level,table[i].adr);</p><p> gendo(del,0,0);//賦值語(yǔ)句需將存入數(shù)組后棧頂為偏移地址出棧</p><p><b> }</b></p><p> else //變量</p><p><b>
90、 {</b></p><p> gendo(sto,lev-table[i].level,table[i].adr); //根據(jù)變量地址存入變量</p><p><b> }</b></p><p><b> }</b></p><p><b> }</b>
91、;</p><p><b> }</b></p><p><b> }</b></p><p> else if(sym==dplus) //++變量</p><p><b> {</b></p><p><b> getsymdo;
92、</b></p><p> if(sym==ident)//后面跟的是變量</p><p><b> {</b></p><p> i=position(id,*ptx);</p><p><b> if(i==0)</b></p><p><b&g
93、t; {</b></p><p> error(11);</p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><p> if(table[i].kind!
94、=variable&&table[i].kind!=array) //++后沒(méi)跟變量,出錯(cuò)</p><p><b> {</b></p><p> error(12);i=0;</p><p><b> }</b></p><p> else //++后跟變量,處理生成中間代
95、碼</p><p><b> {</b></p><p> if(table[i].kind==variable)</p><p><b> {</b></p><p> gendo(lod,lev-table[i].level,table[i].adr);//先取值到棧頂</p>
96、;<p> gendo(lit,0,1);//將值為1入棧</p><p> gendo(opr,0,2);//加法,即+1,棧頂加次棧頂</p><p> gendo(sto,lev-table[i].level,table[i].adr);//出棧取值到內(nèi)存</p><p><b> getsymdo;</b><
97、/p><p><b> }</b></p><p> else if(table[i].kind==array) //后跟數(shù)組</p><p><b> {</b></p><p><b> getsymdo;</b></p><p> if(sy
98、m==lepa)</p><p><b> {</b></p><p><b> getsymdo;</b></p><p> memcpy(nxtlev,fsys,sizeof(bool)* symnum);</p><p> nxtlev[ripa]=true;</p>&
99、lt;p> expressiondo(nxtlev,ptx,lev);</p><p> gendo(tra,0,table[i].size); //生成將數(shù)組下標(biāo)范圍入棧指令</p><p> gendo(jud,0,0); //判斷下標(biāo)合法性</p><p> if(sym!=ripa)</p><p><b>
100、 {</b></p><p> error(26); //缺少]</p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><p> gendo(gar,lev-
101、table[i].level,table[i].adr);</p><p> gendo(lit,0,1);</p><p> gendo(opr,0,2);</p><p> gendo(sar,lev-table[i].level,table[i].adr);</p><p> gendo(del,0,0);</p>
102、<p><b> getsymdo;</b></p><p><b> }</b></p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></
103、p><p> error(27);//缺少[</p><p><b> }</b></p><p><b> }</b></p><p><b> }</b></p><p><b> }</b></p><
104、;p><b> }</b></p><p><b> }</b></p><p> else if(sym==dminus)//--變量</p><p><b> {</b></p><p><b> getsymdo;</b></p
105、><p> if(sym==ident) //后面跟的是變量</p><p><b> {</b></p><p> i=position(id,*ptx);</p><p><b> if(i==0)</b></p><p><b> {</b>
106、</p><p> error(11);</p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><p> if(table[i].kind!=variable&&
107、amp;table[i].kind!=array) //--后沒(méi)跟變量,出錯(cuò)</p><p><b> {</b></p><p> error(12);i=0;</p><p><b> }</b></p><p> else //--后跟變量,處理生成中間代碼</p>&l
108、t;p><b> {</b></p><p> if(table[i].kind==variable)//后跟變量</p><p><b> {</b></p><p> gendo(lod,lev-table[i].level,table[i].adr);//先取值到棧頂</p><p&
109、gt; gendo(lit,0,1); //將值為1入棧</p><p> gendo(opr,0,3);//加法,即-1,棧頂減次棧頂</p><p> gendo(sto,lev-table[i].level,table[i].adr);//出棧取值到內(nèi)存</p><p><b> getsymdo;</b></p>
110、<p><b> }</b></p><p> else if(table[i].kind==array)//后跟數(shù)組變量</p><p><b> {</b></p><p><b> getsymdo;</b></p><p> if(sym==lepa
111、)</p><p><b> {</b></p><p><b> getsymdo;</b></p><p> memcpy(nxtlev,fsys,sizeof(bool)* symnum);</p><p> nxtlev[ripa]=true;</p><p>
112、; expressiondo(nxtlev,ptx,lev);</p><p> gendo(tra,0,table[i].size);//生成將數(shù)組下標(biāo)范圍入棧指令</p><p> gendo(jud,0,0);//判斷下標(biāo)合法性</p><p> if(sym!=ripa)</p><p><b> {</b&
113、gt;</p><p> error(26);//缺少]</p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><p> gendo(gar,lev-table[i].l
114、evel,table[i].adr);</p><p> gendo(lit,0,1);</p><p> gendo(opr,0,3);</p><p> gendo(sar,lev-table[i].level,table[i].adr);</p><p> gendo(del,0,0);</p><p>
115、<b> getsymdo;</b></p><p><b> }</b></p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><
116、;p> error(27);//缺少[</p><p><b> }</b></p><p><b> }</b></p><p><b> }</b></p><p><b> }</b></p><p><
117、b> }</b></p><p><b> }</b></p><p> ...//此處省略部分未修改過(guò)的代碼</p><p><b> }</b></p><p> 2.增加Pascal的FOR語(yǔ)句</p><p> 本次課程設(shè)計(jì)中要求擴(kuò)充的是
118、Pascal的FOR語(yǔ)句:</p><p> ?、貴OR <變量>:=<表達(dá)式> TO <表達(dá)式> DO <語(yǔ)句></p><p> ?、贔OR <變量>:=<表達(dá)式> DOWNTO <表達(dá)式> DO <語(yǔ)句></p><p><b> ,流程圖如下:<
119、/b></p><p> 1)在symbol增加字符FORSYM。</p><p> strcpy(KWORD[10],"for"); WSYM[ 10]= forsym;</p><p> strcpy(KWORD[22],"to"); WSYM[22]=tosym;</p><p&
120、gt; strcpy(KWORD[ 7],"downto"); WSYM[ 7]=downtosym;</p><p> 2)對(duì)statement函數(shù)進(jìn)行擴(kuò)充</p><p> int statement(bool* fsys,int * ptx,int lev)</p><p><b> {</b></p&
121、gt;<p> ...//此處省略部分未修改過(guò)的代碼</p><p> else if(sym== forsym)</p><p><b> {</b></p><p><b> getsymdo;</b></p><p> if(sym==ident) // ident為變
122、量的符號(hào)</p><p><b> {</b></p><p> i=position(id,*ptx);</p><p><b> if(i==0)</b></p><p> error(11);</p><p><b> else</b>&
123、lt;/p><p><b> {</b></p><p> if(table[i].kind!=variable) //賦值語(yǔ)句中,賦值號(hào)左部標(biāo)識(shí)符屬性應(yīng)是變量</p><p><b> {</b></p><p> error(12);</p><p><b>
124、; i=0;</b></p><p><b> }</b></p><p><b> else</b></p><p><b> {</b></p><p><b> getsymdo;</b></p><p>
125、; if(sym!=becomes) </p><p> error(13);</p><p><b> else </b></p><p><b> getsymdo;</b></p><p> memcpy(nxtlev,fsys,sizeof(bool)*symnum); </
126、p><p> if(nxtlev[tosym]=true){} // tosym</p><p> else nxtlev[downtosym]=true; // downtosym</p><p> expressiondo(nxtlev,ptx,lev); //處理賦值語(yǔ)句右部的表達(dá)式</p><p> gendo(sto,lev-t
127、able[i].level,table[i].adr); //保存初始值</p><p><b> getsymdo;</b></p><p> cx1=cx; //保存循環(huán)開(kāi)始點(diǎn)</p><p> memcpy(nxtlev,fsys,sizeof(bool)*symnum);</p><p> if(sym
128、==dosym)</p><p><b> {</b></p><p><b> getsymdo;</b></p><p> statement(fsys,ptx,lev); //循環(huán)體處理</p><p> gendo(lod,lev-table[i].level,table[i].ad
129、r); //將循環(huán)變量取出放在棧頂</p><p> gendo(opr,0,2); //循環(huán)變量加長(zhǎng)</p><p> gendo(sto,lev-table[i].level,table[i].adr); //將棧頂?shù)闹荡嫒胙h(huán)變量</p><p> gendo(jmp,0,cx1);//無(wú)條件跳轉(zhuǎn)到循環(huán)開(kāi)始點(diǎn)</p><p>
130、code[cx2].a=cx; //回填循環(huán)結(jié)束點(diǎn)的地址</p><p><b> }</b></p><p><b> else </b></p><p> error(29); //for語(yǔ)句中少了do</p><p><b> }</b></p>&
131、lt;p><b> }</b></p><p><b> }</b></p><p><b> else</b></p><p> error(19); //for后面為賦值語(yǔ)句,賦值語(yǔ)句左部是變量,缺少變量</p><p><b> }</b&
132、gt;</p><p> ...// 此處省略部分未修改過(guò)的代碼</p><p><b> }</b></p><p><b> 3.一維數(shù)組</b></p><p> 1)設(shè)置一維數(shù)組的左右括號(hào):</p><p> ssym['[']=lepa;
133、//一維數(shù)組的左括號(hào)[</p><p> ssym[']']=ripa; //一維數(shù)組的右括號(hào)]</p><p><b> 2)增加指令:</b></p><p> strcpy(&(mnemonic[gar][0]),"gar"); </p><p> strcpy(
134、&(mnemonic[sar][0]),"sar");</p><p> strcpy(&(mnemonic[shd][0]),"shd");</p><p> strcpy(&(mnemonic[del][0]),"del");</p><p> strcpy(&(m
135、nemonic[jud][0]),"jud");</p><p> strcpy(&(mnemonic[tra][0]),"tra");</p><p><b> enum fct{</b></p><p> lit, opr, lod, sto, cal, inte, jmp,
136、 jpc, gar, sar, shd, del, jud, tra,</p><p><b> };</b></p><p> 由于指令有原來(lái)的8條拓展到了14條,故進(jìn)行如下修改</p><p> #define fctnum 14</p><p> 增加的指令意義如下:</p><p>
137、; gar:根據(jù)棧頂?shù)钠频刂窂臄?shù)組中取值到新的棧頂</p><p> sar:根據(jù)次棧頂?shù)钠频刂钒褩m數(shù)闹荡嫒霐?shù)組</p><p> shd:將棧頂?shù)闹迪乱频酱螚m敚瑮m敵鰲?,即次棧頂成為棧?lt;/p><p><b> del:出棧頂</b></p><p> jud:判斷數(shù)組下標(biāo)合法性</p>
138、<p> tra:將數(shù)組的下標(biāo)范圍入棧,gendo(tra,0,數(shù)組下標(biāo)最大值);</p><p> 3)增加標(biāo)識(shí)符類型屬性:</p><p> enum object{</p><p><b> constant,</b></p><p><b> variable,</b>
139、;</p><p><b> procedur,</b></p><p> array, //數(shù)組</p><p><b> };</b></p><p> 4)在block函數(shù)中添加如下代碼:</p><p> for(i=tx0+1;i<=tx;i+
140、+)</p><p><b> {</b></p><p> switch(table[i].kind)</p><p><b> {</b></p><p> case constant: /*常量名字*/</p><p>
141、 ...//此處省略部分未修改過(guò)的代碼</p><p> case variable: /*變量名字*/</p><p> ...//此處省略部分未修改過(guò)的代碼</p><p> case procedur: /*過(guò)程名字*/</p><p> ...//此處省略部分未修改過(guò)的代碼<
142、;/p><p> case array://數(shù)組變量</p><p> printf("%d var-array %s ",i,table[i].name);</p><p> printf("lev=%d addr=%d size=%d\n",table[i].level,table[i].adr,table[i].siz
143、e);</p><p> fprintf(fas,"%d var-array %s",i,table[i].name);</p><p> fprintf(fas,"lev=%d addr=%d size=%d\n",table[i].level,table[i].adr,table[i].size);</p><p>&
144、lt;b> }</b></p><p><b> }</b></p><p><b> }</b></p><p> 5)在enter()函數(shù)添加如下代碼:</p><p><b> switch(k)</b></p><p>
145、;<b> {</b></p><p> case constant: /*常量名字*/</p><p> ...//此處省略部分未修改過(guò)的代碼</p><p> case variable: /*變量名字*/</p><p>
146、...//此處省略部分未修改過(guò)的代碼</p><p> case procedur: /*過(guò)程名字*/</p><p> ...//此處省略部分未修改過(guò)的代碼</p><p> case array: /*數(shù)組名字*/</p><p> table[(*pt
147、x)].level=lev;</p><p> table[(*ptx)].adr=(*pdx)-arraysize;</p><p> table[(*ptx)].size=arraysize;</p><p><b> break;</b></p><p><b> }</b></
溫馨提示
- 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒(méi)有圖紙預(yù)覽就沒(méi)有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 眾賞文庫(kù)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。
最新文檔
- 編譯原理課程設(shè)計(jì)報(bào)告--pl0編譯器的擴(kuò)充
- 編譯原理課程設(shè)計(jì)---pl0編輯器擴(kuò)充
- 編譯原理課程設(shè)計(jì)--對(duì)pl0進(jìn)行擴(kuò)充和修改
- 編譯原理課程設(shè)計(jì)--對(duì)pl0進(jìn)行擴(kuò)充和修改
- 編譯原理課程設(shè)計(jì)--對(duì)PL0進(jìn)行擴(kuò)充和修改.doc
- 課程設(shè)計(jì)---pl0功能擴(kuò)充
- 課程設(shè)計(jì)---pl0功能擴(kuò)充
- pl0功能擴(kuò)充課程設(shè)計(jì)
- 課程設(shè)計(jì)---PL0功能擴(kuò)充.doc
- PL0功能擴(kuò)充課程設(shè)計(jì).doc
- 編譯原理pl0課程設(shè)計(jì)報(bào)告
- 編譯原理課程設(shè)計(jì)-pl_0編譯器及其擴(kuò)充
- 編譯原理課程設(shè)計(jì)報(bào)告---pl0編譯程序改進(jìn)及完善
- 編譯原理實(shí)驗(yàn)報(bào)告pl0
- pl0擴(kuò)展編譯器_設(shè)計(jì)文檔
- 第二章pl0編譯程序-
- 編譯原理課程設(shè)計(jì)--c語(yǔ)言編譯器實(shí)現(xiàn)
- 編譯原理課程設(shè)計(jì)--c語(yǔ)言編譯器實(shí)現(xiàn)
- c語(yǔ)言編譯器實(shí)現(xiàn)-編譯原理課程設(shè)計(jì)
- 編譯原理課程設(shè)計(jì)---c語(yǔ)言編譯器的實(shí)現(xiàn)
評(píng)論
0/150
提交評(píng)論