tiểu luận môn Nguyên lý các ngôn ngữ lập trình. Đề tài tìm hiểu bộ công cụ Flex, Bison, ứng dụng trong phân tích từ Vựng và phân tích cú pháp của một ngôn ngữ nào đó - Pdf 34

TRƯỜNG ĐẠI HỌC BÁCH KHOA HÀ NỘI
VIỆN ĐÀO TẠO SAU ĐẠI HỌC
=====o0o=====

BÀI TẬP LỚN
MÔN: NGUYÊN LÝ NGÔN NGỮ LẬP TRÌNH

Giáo viên giảng dạy: TS. Nguyễn Hữu Đức

Đề tài: Tìm hiểu bộ công cụ Flex, Bison, ứng dụng trong phân tích từ
Vựng và phân tích cú pháp của một ngôn ngữ nào đó

NHÓM: 10
Lớp: CH2012B

Sinh viên thực hiện:
Nguyễn Thành Đô
Nguyễn Xuân Trường
Trần Văn Trung
Nguyễn Thị Thùy Dương

Hà Nội, tháng 12/2012


I.

GIỚI THIỆU
Ta sẽ phải tốn rất nhiều thời gian để tìm hiểu và xây dựng một trình trình biên dịch hoàn chỉnh một cách

thủ công. Trên thực tế, đã có rất nhiều công cụ có khả năng phát sinh ra bộ phân tích từ vựng và bộ phân tích cú
pháp. Một trong những bộ cổ điển nhất là lex và yacc – được phát minh tại Bell Lab trong thập niên 1970.



Mô tả
Các hằng số với các kiểu dữ liệu (số nguyên, số thực,

CONSTANT

…)

một

1.
tả
số

Chuỗi hằng (ví dụ “hello world”)

STRING_VALUE

Các danh biểu trong chương trình, bao gồm tên biến,

IDENTIFIER

tên hàm (bắt đầu là chữ cái, theo sau là chữ hoặc số)

IF

Lệnh if

ELSE


Hình 1 .Giao thức liên hệ của bộ phân tích từ vựng.


Qua đó, trình phân tích từ vựng sẽ nhận những định nghĩa về token từ trình phân
tích cú pháp và sẽ trả về token phù hợp.
Chính sự giao tiếp đơn giản này đã khiến cho bộ phân tích từ vựng tỏ ra khá độc
lập so với các phần còn lại của trình biên dịch. Theo giao thức đã trình bày ở Hình , trình
phân tích từ vựng chỉ liên hệ trực tiếp với trình phân tích cú pháp trong vai trò như một
thủ tục. Do đó, một sự thay đổi dù lớn hay nhỏ ở trình phân tích từ vựng cũng không gây
ảnh hưởng đến hoạt động chung của trình biên dịch.
Tuy nhiên, có một số trường hợp mà trình phân tích từ vựng, trình phân tích cú
pháp và bảng danh biểu cần có sự liên hệ mật thiết với nhau để xử lý.
Ví dụ 2: Khai báo kiễu dữ liệu do người dùng tự định nghĩa
typedef int Dummy;
Hoặc
struct Dummy
{
int first, second;
};
Từ cấu trúc khai báo trở đi, Dummy khi được sử dụng sẽ không được hiểu là một danh
biểu nữa mà phải là một từ dành riêng, một kiểu dữ liệu do người dùng định nghĩa. Vì vậy,
bộ phân tích từ vựng sẽ trả về một token đặc biệt khác để bộ phân tích cú pháp có thể
nhận dạng Dummy như một kiểu dữ liệu.
Một công việc nữa của bộ phân tích từ vựng là xác định loại hằng số và chuyển
sang dạng lưu trữ thích hợp (từ dạng dữ liệu nhập là chuỗi).
Ví dụ 3: Với các biễu diễn:
0b1010

: biểu diễn nhị phân của số 10

cách xây dựng cây phân tích cú pháp bắt đầu từ nút gốc.
• Phân tích cú pháp từ dưới lên (Bottom-Up Parsing): bộ phân
tích cú pháp sẽ bắt đầu từ chuỗi token và cố gắng tìm kiếm
luật sinh thích hợp để có thể dẫn về ký tự bắt đầu của văn
phạm.

ngôn ngữ nguồn
token
Trình phân tích từ vựng

cây phân tích cú pháp
Trình phân tích cú pháp

biểu diễn trung gian
Phần còn lại của chuyến trước

yêu cầu token

Bảng danh biểu

Hình 2. Vị trí của trình phân tích cú pháp trong chuyến trước của trình biên dịch
IV.

Bộ công cụ Flex và Bison


1. Bộ phát sinh trình phân tích từ vựng FLEX
a.

Cấu trúc.



File mô tả nguồn
lex.l

FLEX Compiler

lex.yy.c

C Compiler

lex.out

lex.out

chuỗi token

Chương trình nguồn

lex.yy.c

Hình 1. Quá trình phân tích từ vựng

Sau khi được phát sinh từ tập biểu thức chính quy, bộ phân tích từ vựng sẽ được định nghĩa như một
hàm trả ra token tiếp theo (TOKEN yylex();). Khi yylex() được gọi, nó sẽ phân tích chương trình nguồn
thành từng đơn vị từ vựng và tìm biểu thức chính quy phù hợp với những đơn vị từ vựng đó. Khi có sự đối sánh
xuất hiện, yylex() sẽ thực hiện phần mã C tương ứng với biểu thức chính quy được chọn.

c. Một số hàm hỗ trợ.
int main() :

thúc bằng ký tự “ nhưng chưa xét tới trường hợp chuỗi có thể chứa ký tự “ ở giữa như
“string with a \” in it”. Rõ ràng đây là chuỗi hợp lệ và ta nhận dạng ký tự ” ở giữa
bằng ký tự \. Do đó, khi yytext[yyleng – 2] == ‘\\’, tức là ký tự trước ký tự nháy kép
là ký tự \ thì ta không dừng lại mà tiếp tục xét chuỗi nhập cho đến khi gặp ký báo hiệu kết
thúc chuỗi thực sự (yymore())
ECHO
Xuất lexeme hiện tại ra màn hình console (stdout).

2.

Bộ phát sinh trình phân tích cú pháp BISON
a. Cấu trúc.

Tương tự như FLEX, Bison nhận input là một file bao gồm các đặc
tả của một ngôn ngữ. Từ đó, Bison biên dịch ra bộ phân tích cú pháp
bằng mã C để chạy cùng với chương trình. Cấu trúc của file đặc tả
ngôn ngữ cũng gồm 3 phần :


- Phần khai báo:
a. Khai báo C thông thường (biến, prototype hàm, cấu trúc, đĩnh

nghĩa...), được giới hạn trong %{ và %} như FLEX.
b. Khai báo kiểu dữ liệu của các thuộc tính tổng hợp.
c. Khai báo các token và các thuộc tính kết hợp với token (nếu
có).
d. Khai báo các thuộc tính kết hợp với các ký hiệu không kết thúc.
Ví dụ 1: Văn phạm thuộc tính của một số ký hiệu không kết thúc trong file input
của Bison.
%union {

Hành vi ngữ nghĩa của Bison là một chuỗi các lệnh mã C với:



$$ Giá trị thuộc tính kết hợp với ký hiệu chưa kết thúc bên vế trái

của luật sinh.
• $n Giá trị thuộc tính kết hợp với ký hiệu văn phạm thứ n (ký hiệu kết
thúc hoặc chưa kết thúc) của vế phải.
-

Các hàm hỗ trợ.

Ngôn ngữ chủ yếu để mô tả các luật hình thành nên parser là
CFG (văn phạm phi ngữ cảnh). Và dạng tiêu chuẩn để mô tả một CFG
mà BISON áp dụng là BNF (Backus-Naur Form) [5]– từng được dùng để
miêu tả ngôn ngữ Algol 60.
Ví dụ 3: Mô tả dạng BNF cho ngôn ngữ xây dựng biểu thức đơn giản
<s> ::= <e>
<e> ::= <e> ‘+’<t>
|
<t>
<t> ::= <t> ‘*’ <f>
|
<f>
<f> ::= ‘(‘ <e> ‘)’
|
NUM
Mỗi dòng là một luật sinh chỉ ra cách hình thành nên một
nhánh của cây phân tích cú pháp. Bison đã đơn giản hóa BNF để

Quy trình vận hành.
Bison nhận tập tin mô tả ngữ pháp (luật sinh, luật ngữ nghĩa) để
qua đó phát sinh ra bộ phân tích cú pháp (viết bằng ngôn ngữ C). Bộ
phân tích cú pháp này cũng sẽ được biên dịch chung với chương trình

--defines

và được sử dụng như một thủ tục (yyparse()).

Mô tả tập luật sinh, luật ngữ nghĩa (*.y)

--verbose Bản mô tả các trạng thái (y.out)

Bison

Bản định nghĩa các token
Bộ phân
(yyout.h)
tích cú pháp bằng mã C (yyout.c)

Hình 2. Quá trình phân tích cú pháp của BISON

Khi yyparse() được gọi, nó sẽ dựa vào trạng thái hiện tại và
bảng ACTION-GOTO để chọn ra hành vi thích hợp, đồng thời, thực hiện
luật ngữ nghĩa ứng với văn phạm sau khi rút gọn. Ngoài ra, BISON
cũng có thể tạo ra file định nghĩa các token (đã khai báo) được sử
dụng chung trong trình phân tích từ vựng cũng như trình phân tích cú
pháp.
Phương pháp phân tích dưới lên sử dụng một Stack để lưu trữ thông tin về cây con
đã được phân tích. Chúng ta có thể mở rộng Stack này để lưu trữ giá trị thuộc tính tổng


Nhờ tải bản gốc

Tài liệu, ebook tham khảo khác

Music ♫

Copyright: Tài liệu đại học © DMCA.com Protection Status