資電學院
This presentation is the property of its rightful owner.
Sponsored Links
1 / 96

第八章 系統程式 PowerPoint PPT Presentation


  • 105 Views
  • Uploaded on
  • Presentation posted in: General

資電學院 計算機概論 F7810. 第八章 系統程式. 陳邦治編著 旗標出版社. 本章重點. 電腦系統是由硬體及軟體所組成 軟體可分為系統程式 ( 或稱為系統軟體 ) 與應用程式 ( 或稱為應用軟體 ) 二類 本章將介紹系統程式中較具代表性的軟體 由於作業系統將在第九章介紹,因此本章的介紹不包括作業系統. 大綱. 電腦軟體分類 組譯程式 巨集處理程式 前置處理程式 連結載入程式 編譯程式. 3. 3. 電腦軟體分類 . 電腦系統是由硬體及軟體所組成 軟體可分為 應用軟體 (application software)

Download Presentation

第八章 系統程式

An Image/Link below is provided (as is) to download presentation

Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author.While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server.


- - - - - - - - - - - - - - - - - - - - - - - - - - E N D - - - - - - - - - - - - - - - - - - - - - - - - - -

Presentation Transcript


2966403

資電學院計算機概論F7810

第八章

系統程式

陳邦治編著

旗標出版社


2966403

本章重點

  • 電腦系統是由硬體及軟體所組成

  • 軟體可分為系統程式(或稱為系統軟體)與應用程式(或稱為應用軟體)二類

  • 本章將介紹系統程式中較具代表性的軟體

  • 由於作業系統將在第九章介紹,因此本章的介紹不包括作業系統


2966403

大綱

  • 電腦軟體分類

  • 組譯程式

  • 巨集處理程式

  • 前置處理程式

  • 連結載入程式

  • 編譯程式

3

3


2966403

電腦軟體分類

  • 電腦系統是由硬體及軟體所組成

  • 軟體可分為

    • 應用軟體(application software)

    • 系統軟體(system software)

  • 應用軟體是為了處理某個特定的問題而撰寫的程式,應用軟體也可稱為應用程式(application program)


2966403

應用軟體基本定義

  • 應用軟體是為了處理某個特定的問題而撰寫的程式,應用軟體也可稱為應用程式(application program)

  • 常用的應用軟體有二類,分別是:

    • 市售套裝軟體

      • 如電腦遊戲軟體、文書處理軟體及多媒體軟體等等

    • 使用者自行撰寫的程式


2966403

系統軟體基本定義

  • 系統軟體是指電腦系統為維特正常運作或開發應用程式所不可缺少的軟體

    • 如作業系統(Operating System;OS)、組譯程式(assembler)、編譯程式(compiler)、直譯程式(interpreter)、載入程式(loader)、連結程式(linker)、巨集處理程式(macro processor)、前置處理器(preprocessor)及公用程式(utility)等軟體

  • 系統軟體有時也可稱為系統程式(system program)


2966403

應用軟體

  • 市售套裝軟體是最常用的應用軟體

  • 常見的套裝軟體有

    • 「文書處理軟體」、「電子試算表軟體」、「簡報軟體」、「繪圖及影像管理軟體」、「多媒體軟體」、「通訊軟體」及「資料庫管理系統」等,下表為常用的套裝軟體的細部分類及範例


2966403

套裝軟體的細部分類及範例


2966403

套裝軟體的細部分類及範例(cont.)


2966403

常用的系統軟體的功能及範例


2966403

常用的系統軟體的功能及範例 (cont.)


Assembler

組譯程式 (assembler)

  • 組譯程式的功能是將組合語言寫成的原始程式翻譯成目的碼

  • 組譯程式功能圖

組合語言程式是由指令及資料組成。常用的指令有二種,分別是機器指令(machine instruction)與虛擬指令(pseudo instruction)。機器指令經由組譯程式處理後會產生目的碼;虛擬指令的主要作用是標明程式的開始處及結束處,或給予組譯程式指引,因此虛擬指令經由組譯程式處理後通常不會產生目的碼


2966403

組譯程式的工作及輸出

  • 組譯程式應執行的工作有以下 5 項

    • 將機器指令轉換成相對應的機器碼

    • 將符號運算元(symbolic operand)轉換成相對應的機器位址

    • 以機器所能接受的格式產生機器指令

    • 將資料常數(constant)轉換成機器內部的表示法

    • 產生的目的碼(object code)及組合程式列表


2966403

目的碼之基本內容

  • 組譯程式處理完原始程式碼後將產生目的碼,而目的碼之基本內容應有以下三種

    • 標頭記錄(head record)

      • 記載程式的名稱,程式的起始位址以及程式的長度等三種資訊

    • 本文記錄(text record)

      • 記載程式的內容,包括指令的機器碼,欲載入的位址及資料

    • 結束記錄(end record)

      • 記載程式的結束處,並指定程式第一個開始執行的指令的位址


2966403

組譯程式的分類

  • 組譯程式依不同的處理方式,通常可以分為三類

    • 單次處理組譯程式

    • 兩次處理組譯程式

    • 多次處理組譯程式


Single pass assembler

單次處理組譯程式(single pass assembler)

  • 處理原始程式碼一次並產生的目的碼

  • 單次處理組譯程式允許「後方參考」(backward reference),但不允許「前方參考」(forward reference)動作

    • 「後方參考」指符號先定義,才引用,而「前方參考」則是指符號未定義前就先引用

  • 單次處理組譯程式處理方式如下圖


2966403

單次處理組譯程式(cont.)

  • 因為單次處理組譯程式只掃瞄原始程式碼一次,因此組譯(assemble)時間在三種組譯程式中最短

  • 因目的碼未執行最佳化處理(optimization),執行效率可能稍差


2966403

單次處理組譯程式範例

  • 解:

    AX、BX、CX及DX為暫存器名稱,因此可直接引用不需定義。此程式段中定義的符號共有三個,分別是LOOP、DATA及SIX,因此僅需針對此三個符號說明即可

    (1)「backward reference」指令:JMP LOOP

    (2)「forward reference」指令:SUB BX, SIX及MOV DX, DATA


Two pass assembler

兩次處理組譯程式(two pass assembler)

  • 兩次處理組譯程式的程式結構分為二個部份,分別是Pass 1與Pass 2

  • 先由Pass 1處理原始程式後,輸出「中間碼」,Pass 2再處理「中間碼」後輸出目的碼(請注意:不是處理原始程式二次)

  • Pass1的工作為定義符號(define symbol),而Pass 2的工作則為產生目的程式(generate object code)

  • 兩次處理組譯程式處理方式如下圖

兩次處理組譯程式允許「前方參考」,通常不會對目的碼執行最佳化處理,因此執行效率可能稍差


Multiple pass assembler

多次處理組譯程式(multiple pass assembler)

  • 多次處理組譯程式會作多次掃瞄的動作,因此允許「前方參考」

  • 在第一次處理時先保留這些牽涉到「前方參考」的未定義符號,在往後的幾次處理中再一一的對這些符號作處理

  • 可對目的碼執行最佳化處理,因此執行效率較佳

  • 因多次處理組譯程式會掃瞄程式碼多次,因此組譯時間在三種組譯程式中最長


2966403

多次處理組譯程式範例

  • 請說明以下程式段為何需要三次處理的組譯程式才能處理?

    A EQU B+1

    B EQU C+100

    C EQU 200

  • 解:

    Pass 1: 定義C的值為200

    Pass 2: 定義B的值與C+100相同

    Pass 3: 定義A的值與B+1相同並產生目的碼


Absolute program

絕對程式(absolute program)

  • 「絕對程式」(absolute program)是指必須載入到使用者指定的位址才能執行的程式

  • 事實上在同一時刻可能同時會有多個程式在記憶體中由於無法預知這些程式執行的順序,因此無法事先分配程式所實際佔用的記憶體空間

  • 因為程式在執行過程中可能因為本身之需求或其他程式之需求而必須將程式碼由目前所佔用的記憶體空間,搬移到另一個記憶體空間來執行

  • 基於以上二個原因,可以瞭解「絕對程式」的觀念有嚴重的缺點為滿足程式執行時的實際需求,必須有一種作法可以允許程式能載入不同於原先載入的位址,這種可將程式載入不同於原先載入的位址的動作稱為「重定位」(relocation)


2966403

程式重定位

  • 為了滿足「重定位」之需求,組譯程式輸出之目的碼中應提供資訊給載入程式,再由載入程式來執行修正位址的動作

  • 目的碼中若包含程式載入記憶體時應修改的資料,此種目的碼便稱為「可重定址程式」(relocatable program)

  • 為了提供目的碼「重定位」能力,組譯程式會在目的碼中多輸出一項稱為修飾記錄(modification record)的資料,修飾記錄內記載了目的碼在載入記憶體時需修改的資訊

    • 修飾記錄的內容包含了必須被修改的位址欄位之起始位址及被修改的欄位的長度

  • 假設程式中有goto 敘述。若程式提供「重定位」功能,則goto 敘述後方所指定的敘述之位址便必須隨著程式載入位址的不同而連帶被更改


Overlay structure

覆疊結構 (overlay structure)

  • 「覆疊結構」是指將程式中不會同時執行的部份載入到記憶體中相同的位置執行

  • 兩次處理組譯程式中的Pass 1與Pass 2,因為先執行Pass 1,再執行Pass 2,滿足「不會同時執行」的條件

    • 可讓組譯程式的Pass 1與Pass 2使用相同的記憶體空間來執行,如此一來便可降低兩次處理組譯程式執行時記憶體空間的需求量


2966403

具有覆疊結構的兩次處理組譯程式


2966403

常見定址模式

  • 不同的定址模式提供了取得運算元內容的不同方法

  • 常見定址模式可分為

    • 「立即定址模式」、「直接定址模式」、「間接定址模式」、「索引定址模式」、「基底定址模式」及「相對定址模式」六種


Immediate addressing mode

立即定址模式(immediate addressing mode)

  • 立即定址模式是指運算元為指令的一部份,執行時不必再做額外的記憶體存取動作可立即利用運算元的值作運算

    • 如「move AX,13H」指令運算元的值為13H(16進位的13),不必再做額外的記憶體存取動作


Direct addressing mode

直接定址模式(direct addressing mode)

  • 直接定址模式代表指令中運算元之值為資料存放在記憶體中的位址,必須透過此位址作一次記憶體存取的動作才能取得所需的資料,又稱為絕對位址模式(absolute addressing mode)


Indirect addressing mode

間接定址模式(indirect addressing mode)

  • 間接定址模式是指運算元欄內的值是位址,此位址會指向記憶體中之位置,此位置中存放資料在記憶體中的位址


Index addressing mode

索引定址模式(index addressing mode)

  • 索引定址模式是指將運算元欄位的值加上索引暫存器(index register)之值即為資料的位址。若要變更存取記憶體中的位置則需變更索引暫存器之值


Base addressing mode

基底定址模式(base addressing mode)

  • 基底定址模式是指將運算元欄位的值加上基底暫存器(base register)的值,即為資料的位址。若要變更存取記憶體中的位置則需變更運算元碼之值


Relative addressing mode

相對定址模式(relative addressing mode)

  • 相對定址模式是指將運算元欄位的值加上程式計數器(program counter)內的值,即為資料的位址


2966403

巨集處理程式

  • 設計程式時,經常會將一些相關的敘述集合在一起以節省程式設計的時間,常使用的方式有

    • 迴圈(loop)

    • 副程式(subroutine)

    • 巨集(macro)

  • 迴圈及副程式的觀念請參考本書「程式設計篇」中之介紹,此處僅介紹巨集


2966403

巨集相關觀念

  • 巨集又稱為「巨集指令」(macro instruction),用來代表程式中一群常用的敘述

  • 「巨集定義」(macro definition)的功用是定義巨集及其所對應的一群敘述

  • 「巨集展開」(macro expanding)又稱為「巨集呼叫」(macro call),是指將巨集名稱以相對應的一群敘述取代

  • 程式中的「巨集定義」程式段可利用「巨集呼叫」來呼叫

  • 當語言處理器處理「巨集呼叫」敘述時會利用「巨集展開」的動作以「巨集定義」來取代「巨集呼叫」敘述


2966403

「巨集展開」示意圖


2966403

巨集範例

XXXMACRO&參數

  巨集程式碼

MEND

  • 「XXX」表示巨集名稱

  • 「巨集程式碼」以「XXX」代表其名稱,必須透過「XXX」巨集名稱來呼叫巨集

  • 當程式經由巨集處理程式處理後,巨集處理程式會將程式中所有的巨集名稱替換成相對應的巨集定義內容,因此程式經過巨集處理程式處理後的程式碼將會變長

  • 因為巨集的處理模式是用「字串替代」方式(將一條敘述替換成一段敘述群)

  • 完成巨集處理的程式碼執行時,不會有控制流程(control flow)的轉移,因此執行的速度會比利用副程式設計程式快


2966403

巨集範例


2966403

巨集與副程式的比較


2966403

巨集的優點

  • 使用巨集指令的優點有以下三項

    • 程式較易維護

    • 程式較易除錯

    • 系統較具彈性


C inline

C++語言的inline函式

  • 在某些知名的近代高階語言也提供了巨集處理的功能,如C++語言

  • 在C++語言中提供的「inline函式」便是利用了巨集處理的觀念

  • 「inline函式」的作法是在函式的名稱前加上「inline」關鍵字便可讓此函式成為「inline函式」


C inline1

C++「inline函式」 處理模式


2966403

精選範例

  • 單次處理組譯程式通常需要建立「未定義符號表」,假如不允許建立「未定義符號表」,則在下列五種情形的不同組合下各需幾道組譯器:

    (a) 符號在用到時已定義。

    (b) 符號在用到時未定義。

    (c) 所有巨集指令呼叫均在巨集指令定義之後。

    (d) 巨集指令呼叫可以在巨集指令定義之前。

    (e) EQU 敘述內含有未定義符號。

    AC EQU BASE-1

    BASE EQU 15

    (A) (a)+(c) (B) (b)+(c) (C) (a)+(d)

    (D) (b)+(d) (E) (b)+(c)+(e) (F) (b)+(d)+(e)

  • 解:

    處理巨集的問題主要分為二個部份,一為巨集定義,另一則為巨集展開


2966403

(A)

(a) 符號在用到時已定義

(c) 所有巨集指令呼叫均在巨集指令定義之後

(A)單次處理組譯程式

因為符號及巨集指令均在用到或呼叫時已事先定義好,因此僅需一次處理便可完成所有的工作。執行工作如下:

Pass 1:巨集定義、巨集展開、符號定義、產生目的碼。


2966403

(B)

(b) 符號在用到時未定義。

(c) 所有巨集指令呼叫均在巨集指令定義之後

(B)二次處理組譯程式

由於符號在用到時尚未定義,故需二次處理組譯程式方可處理完成。執行工作分配如下:

Pass 1:巨集定義、巨集展開、符號定義。

Pass 2:產生目的碼。


2966403

(C)

(a) 符號在用到時已定義。

(d) 巨集指令呼叫可以在巨集指令定義之前

(C)二次處理組譯程式

因為 Pass 1 處理符號及巨集的定義,但由於巨集指令的呼叫可在巨集指令定義之前,因此 Pass 1 無法完成組譯工作,故需 2 個 pass 才足夠。執行工作分配如下:

Pass 1:巨集定義。

Pass 2:巨集展開、符號定義、產生目的碼


2966403

(D)

(b) 符號在用到時未定義

(d) 巨集指令呼叫可以在巨集指令定義之前

(D)三次處理組譯程式

(b)符號在用到時未定義:二次處理。

(d)巨集指令呼叫可在巨集指令定義之前:二次處理。

巨集展開與符號定義可合併由一個pass 來處理。故共需3個 pass 來完成這項工作。執行工作分配如下:

Pass 1:巨集定義。

Pass 2:巨集展開、符號定義。

Pass 3:產生目的碼


2966403

(E)

(b) 符號在用到時未定義

(c) 所有巨集指令呼叫均在巨集指令定義之後

(e) EQU 敘述內含有未定義符號

(E)三次處理組譯程式

執行工作分配如下:

Pass 1:巨集定義、巨集展開、符號定義(含第一層EQU符號定義)

Pass 2:繼續處理第二層EQU符號定義

Pass 3:產生目的碼


2966403

(F)

(b) 符號在用到時未定義

(d) 巨集指令呼叫可以在巨集指令定義之前

(e) EQU 敘述內含有未定義符號

(F)四次處理組譯程式

執行工作分配如下:

Pass 1:巨集定義

Pass 2:巨集展開、符號定義(含第一層EQU符號定義)

Pass 3:繼續處理第二層EQU符號定義

Pass 4:產生目的碼


2966403

前置處理程式

  • 「前置處理程式」是指程式語言處理器在開始處理程式段之前的處理程式

  • 本節將以C程式語言為例,說明「前置處理程式」之作法

  • 對一個 C 程式而言,程式在被編譯之前,程式會先由C程式語言的「前置處理程式」先負責處理含有「#」開頭的敘述後(如#include 、#define等),再將結果檔交由編譯程式處理後續工作


2966403

C 語言前置處理程式處理流程圖


2966403

前置處理程式範例

利用C語言定義一敘述如下:

#define square(x) x*x

square(x)的用途為傳回x的平方值(如執行square(7),執行結果為49),若x為4+3則執行結果為何?

解:19

C語言處理此類問題時,不會先行計算4+3=7之結果,再將7傳入square(x)中計算,而是直接將4+3傳入,因此實際計算過程如右


2966403

連結載入程式

  • 當原始程式經過程式語言處理器處理後(編譯或組譯),再經連結(linking)成可執行的程式碼後,最後便必須被「載入」主記憶體中等候執行

  • 此處所指的「載入」工作便是由載入程式所負責

  • 因此載入程式所負責的工作是將程式碼由輔助記憶體載入主記憶體中等候執行


2966403

載入程式的工作

  • 配置記憶體空間 (allocation)

    • 要求作業系統配置空間供程式載入使用。

  • 連結(linking)

    • 解決不同程式段之間彼此相互參考的問題,即解決「外部符號」(external symbol)的引用問題。「外部符號」是指不在本地程式段內定義之符號。

  • 重定址(relocation)

    • 調整目的程式中與記憶體相關的指令或資料使程式能載入不同於原先載入的位置。

  • 載入(loading)

    • 將程式載入主記憶體中

注意:只要能夠完成上述第四項「載入」工作之程式,便是載入程式;並不是所有的載入程式都能完成以上四項工作


2966403

載入程式的分類

  • 載入程式的種類很多,依其功能及特性的不同可分為四種

    • 「絕對載入程式」(absolute loader)

    • 「組譯並執行載入程式」(assemble-and-go loader)

    • 「可重定址載入程式」(relocatable loader)

    • 「連結編輯程式」(linkage editor)


2966403

絕對載入程式

  • 「絕對載入程式」僅負責載入工作,另外三項工作負責單位如下:

    • 配置記憶體空間:程式設計師。

    • 連結:程式設計師。

    • 重定址:組譯程式。

  • 因為程式設計師必須負責配置記憶體空間及連結二項工作,因此對程式設計師而言具有較大的自主權;但相對地,程式設計師必須牢記副程式的位址及安排目的碼的載入位址,所以負擔很大

  • 「絕對載入程式」無法自行處理重定位問題


2966403

組譯並執行載入程式

  • 此類載入程式為直譯式作法

  • 當原始程式被翻譯成機器語言後就直接被放置在主記憶體內,待原始程式全部翻譯完成,便馬上開始程式的執行動作

  • 若採用「組譯並執行載入程式」,當程式要執行時,每次都必須重新翻譯,因此執行效率較差


2966403

可重定址載入程式

  • 此類載入程式允許程式段可調整載入記憶體中之位址


2966403

連結編輯程式

  • 對不同程式段合併執行連結(linking)動作並產生產生「已連結程式」(linked program)或稱為「載入模組」(load module)

  • 當程式執行時才處理重定址及載入工作

  • 具有較佳的執行效率之特性


2966403

範例

  • 「絕對載入程式」如何處理「重定位」問題?

  • 解:

    必須透過組譯程式重新翻譯原始程式碼,才可處理「重定位」問題


2966403

連結程式

  • 連結程式(linker)的工作是解決不同程式段間彼此相互參考的問題

    • 就是解決「外部符號」的參考問題

  • 「外部符號」指的是不在本地定義的符號,可能是函式庫(library)內的函式,或是其他程式段內定義的函式或符號

  • 連結程式會將程式中所使用到外部符號連結起來,並產生完整的執行檔

  • 假設程式由多人分工合作完成,此時參與程式開發工作的程式設計師可各別完成自己的程式段,每個原始程式都可個別編譯(separate compile)成目的碼,然後再利用連結程式將這些目的檔連結合併成一個完整的執行檔


2966403

連結程式處理流程


Dynamic loading

動態載入(dynamic loading)

  • 「動態載入」是指將程式的載入的動作,延遲到程式執行的時候才處理

  • 真正會被執行到的程式才做載入的動作

  • 「動態載入」可利用覆疊(overlay)及虛擬記憶體(virtual memory)技術來達成


Dynamic linking

動態連結(dynamic linking)

  • 動態連結是指將連結的動作,延遲到程式執行時才處理

  • 真正會被執行到的程式段才執行連結處理動作

  • 程式在執行過程中,可能有部份的符號或副程式並不會被引用或呼叫,因此如果在連結時便將這些未被引用或呼叫的符號或副程式連結進來,將增加連結程式的負擔,同時也增加了記憶體空間的需求量


2966403

範例

  • 若系統採用「動態連結」機制,當副程式執行完畢時,其控制流程的轉移方式,與一般副程式呼叫後控制流程的轉移方式是否相同?

  • 解:不同

    「動態連結」實作機制如下:

    • 首先,程式提出一個系統呼叫給作業系統並將副程式的名稱傳給作業系統,然後程式的控制權將轉移給作業系統

    • 接下來,作業系統將檢查此副程式是否已經在記憶體中

      • 若副程式已在記憶體中則直接開始副程式之執行,待副程式執行完畢,程式控制權必須交還給作業系統,再由作業系統將控制權交還給程式

      • 若副程式不在記憶體中,便必須由動態連結程式庫(dynamic link library)中將副程式連結並載入主記憶體中。待副程式載入主記憶體後,開始副程式之執行,當副程式執行完畢時,程式控制權必須交還給作業系統,再由作業系統將控制權交還給程式


2966403

「動態連結」實作機制


2966403

範例

請說明「組合語言」、「組譯程式」與「連結載入程式」(linking loader)三者之間如何完成「符號連結」工作(symbolic linking)。

解:

「符號連結」是指解決外部符號參考的問題。

組合語言利用「EXTDEF」及「EXTREF」指令來指定變數的類別,並將資訊提供給組譯程式。

如以下範例:

EXTDEF A, B, C // 代表A, B, C三個變數在本地定義,但可被外部程式段引用。

EXTREF D, E // 代表E, F二個變數不在本地定義,但可引用。

組譯程式必須將程式中宣告為「EXTDEF」及「EXTREF」型態的變數特別記錄下來,並將資料提供給連結載入程式做為符號連結工作使用。


Compiler

編譯程式(compiler)

  • 編譯程式的作用是將利用高階語言寫成的原始程式(source program)翻譯成目的碼(object code)

  • 編譯程式會對原始程式碼中的每一條敘述,按照先後順序均做一次之轉換處理,並產生對應之目的碼,這種轉換處理的工作必須完全遵守採用的程式語言所規定的文法規則(grammar rules)

  • 不同程式語言的文法規則是不相同的。若撰寫程式時違背了程式語言的文法規則,編譯時將會發生文法錯誤之訊息


2966403

文法四要素

  • 文法(grammar)是由四個要素所構成

    • 分別為終端符號(terminal symbol,簡寫為「T」),非終端符號(non-terminal symbol,簡寫為「N」),起始符號(starting symbol,簡寫為「S」)與文法產生規則(production rule,簡寫為「P」)

    • 終端符號表示不能再以其他符號來替代。非終端符號表示可以再以其他符號來替代

    • N與T須滿足以下的關係:N∩T = 

    • 從事文法推演之步驟由S開始且SN


2966403

文法產生規則須符合條件

  • 文法產生規則須符合下列條件:

    • u→vP,其中u(NT)+且v(NT)*

    • 其中

      • (NT) +:代表由非終端符號與終端符號所組成的任意長度之字串,但不得為空字串

      • (NT)* :代表由非終端符號與終端符號所組成的任意長度之字串。


2966403

範例

範例:

若T={a}, N={A},請說明(NT)+及(NT)*的結果值為何?

解:

(NT)+的結果值如下:

{a, A, aa, aA, Aa, AA, aaa, aaA, aAa, aAA, Aaa, AaA, AAa, AAA, …..}共有無限多種可能。

(NT)* 的結果值如下:

{λ, a, A, aa, aA, Aa, AA, aaa, aaA, aAa, aAA, Aaa, AaA, AAa, AAA, …..}共有無限多種可能,其中「λ」代表空字串


2966403

文法的分類 (1/3)

  • Type 0:

    無任何限制。

    Type 0文法所產生之Language可利用Turing Machine辨識。

  • Type 1:

    與上下文相關的文法(context-sensitive grammar),其文法產生規則必須滿足以下規則:

    u→vP,|u||v|

    Type 1文法所產生之Language可利用線性限制自動機(Linear Bounded Automata)辨識且規定文法產生規則左方的符號長度不得大於右方的符號長度


2966403

文法的分類 (2/3)

  • Type 2:

    與上下文無關的文法(context free grammar),又稱為BNF文法

    文法產生規則必須滿足以下規則:

    u→vP,其中uN,v(NT)*-λ

    Type 2文法所產生之Language可利用推壓自動機(Push Down Automata)辨識且規定文法產生規則左方僅允許長度為1之非終端符號


2966403

文法的分類 (3/3)

Type 3:正規文法(regular grammar)

Type 3文法所產生之Language可利用有限狀態自動機(Finite State Automata)辨識且規定文法產生規則左方僅允許長度為1之非終端符號,而文法產生規則右方則僅允許長度為1之終端符號

正規文法又分為二類:

(1)右線性正規文法(right linear regular grammar)其文法產生規則需滿足以下規則:

A→uB or A→u,其中A,BN,uT

(2)左線性正規文法(left linear regular grammar)其文法產生規則需滿足以下規則:

A→Bu or A→u,其中A,BN,uT


2966403

BNF文法

  • 由於近代高階語言的文法多採BNF文法來描述,因此本節將針對BNF文法之特性與作法做介紹

  • BNF文法常用的符號整理如下表


2966403

範例

若有一個BNF文法規則定義如下:

<A>::= <A> + <A>|<A> - <A>|<A> * <A>|<A> / <A>|id

請根據以上的文法規則,推導出id*id+id/id 。

解:

根據題目的文法規則,id*id+id/id的推導過程如下:


2966403

剖析樹

  • 剖析樹是根據語言的 B.N.F. 描述,將敘述轉換成相對應的樹狀結構,此樹狀結構被稱為剖析樹。剖析樹會比文法推導式具備較高的可讀性及較易理解

  • 利用上例來說明,對應的剖析樹產生過程如右圖所示


Ambiguous grammar

模擬兩可的文法(ambiguous grammar)

  • 「模擬兩可的文法」

    • 「混淆的文法」或「曖昧的文法」

    • 文法定義不完備,可能導致程式執行結果不唯一

  • 「模擬兩可的文法」正式的定義如下:

    • 根據語言的 B.N.F. 描述,對同一敘述可繪出二個或二個以上不同的剖析樹,則稱此語言的文法是模擬兩可的


2966403

範例

以前題為例,id*id+id/id的另一推導過程如下:

<A> ::= <A> * <A>::= id * <A>::= id * <A> + <A>::= id * id + <A>::= id * id + <A> / <A>::= id * id + id / <A>::= id * id + id / id

對「id*id+id/id」敘述而言,根據<A>::= <A> + <A>|<A> - <A>|<A> * <A>|<A> / <A>|id文法規則可繪出以上二種不同的剖析樹,所以此文法規則為模擬兩可的文法


2966403

編譯程式的工作

  • 編譯程式的功能是處理高階語言寫成的原始程式,並產生可在機器上執行的目的碼

  • 編譯程式主要的工作依序可分為

    • 「語彙分析」(lexical analysis)、「語法分析」(syntax analysis)、「語意分析」(semantic analysis)、產生「中間碼」(intermediate form generate)、「最佳化」(optimization)及「目的碼產生」(object code generate)共六個階段


2966403

語彙分析

  • 利用語彙分析器(lexical analyzer),處理原始程式進行語彙分析工作

  • 語彙分析是指將原始程式的內容切割成文法基本元素「token」

  • 以C語言之敘述「a=b+c;」為例

    • 「a=b+c;」敘述共可切割成6個tokens,分別是「a」、「=」、「b」、「+」、「c」及「;」


2966403

語法分析

  • 利用語法分析器(syntax analyzer),進行語法分析工作

  • 語法分析是指根據文法產生規則,將token組合成剖析樹


2966403

語意分析

  • 利用語意分析器(semantic analyzer),進行語意分析工作

  • 語意分析是指根據剖析樹判斷敘述是否合乎語意規定並轉換成動作表(action list)


2966403

產生中間碼

  • 把動作表轉換成中間碼


2966403

最佳化

  • 對中間碼執行「與機器無關最佳化」工作


2966403

目的碼產生

  • 依據最佳化的中間碼產生目的碼


2966403

編譯程式最佳化

  • 編譯程式執行最佳化動作的目的是為了加快執行的速度,而最佳化動作可分為二大類

    • 「與機器無關最佳化」(machine independent optimization)

    • 「與機器相關最佳化」(machine dependent optimization)


2966403

與機器無關最佳化

  • 將迴圈中不變的運算式或值移到迴圈外

  • 編譯時期計算(compile time computation)

  • 簡化共同的子運算式(sub-expression)

  • 捷徑計算(short circuit evaluation)


2966403

將迴圈中不變的運算式或值移到迴圈外

s=0;

for (i=1; i<=100; i++)

{

s = s+i;

a=5;

}

可最佳化為以下程式段:

s=0;

a=5;

for (i=1; i<=100; i++)

s = s+i;


2966403

編譯時期計算

若程式中的運算式中有部份運算的值可先在編譯時期計算,就不須等到執行時才計算

例如,

s = (x+4*6/3)/y;

可最佳化為以下程式段:

s = (x+8)/y;


2966403

簡化共同的子運算式

例如,

x = a*b+c*d-e;

y = c*d+a*b-f+g;

可最佳化為以下程式段:

u = a*b;

v=c*d;

x = u+v-e;

y = v+u-f+g;


2966403

捷徑計算

捷徑計算是指對運算式(通常是指布林運算式)作求值動作時,無需做完整個運算式即可得出最後的結果。

例如,

X1 and X2:

若X1為false則運算式的結果為false,不需再計算此運算式中X2 之值即可決定最後的結果值。

X1 or X2:

只要X1為true則運算式的結果為true,不需再計算此運算式中X2 之值即可決定最後的結果值


2966403

與機器相關最佳化

  • 與機器相關最佳化可分為3種不同的作法

    • 去除多餘的(redundent)指令碼

    • 調整指令執行的順序

    • 多使用暫存器(register)存放變數


2966403

去除多餘的指令碼

將程式中多餘的指令碼去除

例如,

………

MOV AX, BX

MOV AX, CX

………

可最佳化為:

………

MOV AX, CX

………


2966403

調整指令執行的順序

例如,

………

MUL BX, AX

MUL CX, AX

ADD BX, CX

………

可最佳化為:

………

ADD BX, CX

MUL BX, AX


Compiler s compiler

編譯程式的編譯程式(Compiler’s compiler)

  • 編譯程式的編譯程式是指利用程式語言自己的語法來撰寫自己的編譯程式


2966403

範例

  • 假設有一個C語言的子集合X語言,X語言除了不具備for-loop、while-loop及do while- loop三種迴圈結構之功能外,其餘的功能、指令、提供的資料型態或語法等規定均與C語言相同

  • 我們可先針對X語言設計出X語言的編譯程式,再利用X語言之語法來設計C語言的編譯程式

  • 由於X語言本身為C語言的子集合,因此利用X語言之語法來設計C語言的編譯程式相當於利用C語言之語法來設計C語言的編譯程式


  • Login