You are on page 1of 4

Báo cáo: Ngôn ngữ và phương pháp dịch

Báo cáo Chương trình dịch


Bài số 1. Phân tích từ vựng
Bài số 2. Phân tích cú pháp
Bài số 3. Phân tích ngữ nghĩa

Bài số 1. Phân tích từ vựng – bộ scanner

1. Nhiệm vụ của bộ scanner


o Bỏ qua các ký tự vô nghĩa như: dấu trống, tab, ký tự xuống dòng, chú
thích.
o Phát hiện các ký tự không hợp lệ
o Phát hiện token
 định danh (identifier)
 từ khóa (keyword)
 số (number)
 Hằng ký tự
 special symbol
 ...
o Chuyển lần lượt các token cho bộ phân tích cú pháp

2. Xây dựng scanner


Bộ scanner bao gồm:
STT Tên tệp Nội dung chính
1 scanner.h, scanner.c Đọc từng token
2 reader.h, reader.c Đọc mã nguồn
3 charcode.h, Phân loại ký tự
charcode.c
4 token.h, token.c Phân loại, nhận dạng token và từ khóa
5 error.h, error.c Thông báo lỗi

Cụ thể :
Reader
// Đọc một ký tự từ kênh vào
int readChar(void);
// Mở kênh vào
int openInputStream(char *fileName);
// Đóng kênh vào
void closeInputStream(void);
Báo cáo: Ngôn ngữ và phương pháp dịch

// Chỉ số dòng, cột hiện tại


int lineNo, colNo;
// Ký tự hiện tại
int currentChar;

Charcode : charcode.c định nghĩa một bảng charCodes ánh xạ từng ký tự trong bảng mã
ASCII vào một trong các CharCode được định nghĩa
Token:

// Cấu trúc lưu trữ của một token


typedef struct {
char string[MAX_IDENT_LEN + 1];
int lineNo, colNo;
TokenType tokenType;
int value;
} Token;
// Kiểm tra một xâu có là từ khóa không
TokenType checkKeyword(char *string);
// Tạo một token mới với kiểu và vị trí
Token* makeToken(TokenType tokenType, int lineNo, int colNo);

Một số hàm chính trong scanner.c


Token* getToken(void); // Doc mot token moi
Token* getValidToken(void); // Doc mot token hop le chuyen sang cho
bo phan tich cu phap
void printToken(Token *token); // In token

void skipBlank(); // Bo qua cac khoang trong


void skipComment(); // Bo qua comment
Token* readIdentKeyword(void); // Doc mot dinh danh
Token* readNumber(void); // Doc mot so
Token* readConstChar(void); // Doc mot hang ky tu

Bài số 2. Phân tích cú pháp – bộ parser

1. Nhiệm vụ của bộ phân tích cú pháp


• Kiểm tra cấu trúc cú pháp của một chương trình
• Kích hoạt các bộ phận phân tích ngữ nghĩa và sinh mã
Báo cáo: Ngôn ngữ và phương pháp dịch

2. Xây dựng bộ phân tích cú pháp

6 parser.h, parser.c Duyệt các cấu trúc chương trình


Một số hàm cơ bản trong parser.c :

Token *currentToken; // Token vừa đọc


Token *lookAhead; // Token xem trước
void scan(void); // Xem trước nội dung một token

void eat(TokenType tokenType); // Duyệt ký hiệu kết thúc


void compileProgram(void); // Duyệt ký hiệu không kết thúc

Kích hoạt parser:


int compile(char *fileName) {
if (openInputStream(fileName) == IO_ERROR)
return IO_ERROR;
currentToken = NULL;
lookAhead = getValidToken();
compileProgram();
free(currentToken);
free(lookAhead);
closeInputStream();
return IO_SUCCESS;
}

Từ hàm compileProgram, chương trình phân tích cú pháp theo văn phạm BNF của ngôn
ngữ KPL (theo slide).

Bài số 3. Phân tích ngữ nghĩa


1. Nhiệm vụ của bộ phân tích ngữ nghĩa.
o Quản lý thông tin về các định danh: Hằng, biến, kiểu người dùng định
nghĩa, chương trình con (hàm, thủ tục)
o Kiểm tra một số luật ngữ nghĩa : phạm vi định danh, nhất quán kiểu…

2. Xây dựng bảng ký hiệu.


Bảng ký hiệu: Lưu trữ thông tin về các định danh trong chương trình và các thuộc tính
của chúng.
• Hằng: {tên, kiểu, giá trị}
• Kiểu người dùng định nghĩa: {tên, kiểu thực tế}
• Biến: {tên, kiểu}
Báo cáo: Ngôn ngữ và phương pháp dịch

• Hàm: {tên, các tham số hình thức, kiểu trả về, các khai báo địa phương}
• Thủ tục: {tên, các tham số hình thức, các khai báo địa phương)
• Tham số hình thức: {tên, kiểu, tham biến/tham trị}
Các thành phần của bảng ký hiệu:
// Bảng ký hiệu // Phạm vi của một block
struct SymTab_ { struct Scope_ {
// Chương trình chính // Danh sách các đối tượng
Object* program; //trong block
// Phạm vi hiện tại ObjectNode *objList;
Scope* currentScope; // Hàm, thủ tục, chương trình
// Các đối tượng toàn cục như // tương ứng block
// hàm WRITEI, WRITEC, WRITELN Object *owner;
// READI, READC // Phạm vi bao ngoài
ObjectNode *globalObjectList; struct Scope_ *outer;
}; };

Mỗi đối tượng được quản lý bởi cấu trúc Object:


enum ObjectKind { struct Object_ {
OBJ_CONSTANT, char name[MAX_IDENT_LEN];
OBJ_VARIABLE, enum ObjectKind kind;
OBJ_TYPE, union {
OBJ_FUNCTION, ConstantAttributes*
OBJ_PROCEDURE, constAttrs;
OBJ_PARAMETER, VariableAttributes* varAttrs;
OBJ_PROGRAM TypeAttributes* typeAttrs;
}; FunctionAttributes* funcAttrs;
ProcedureAttributes*
procAttrs;
ProgramAttributes* progAttrs;
ParameterAttributes*
paramAttrs;
};
};

3. Kiểm tra sự trùng lặp khi khai báo đối tượng.

You might also like