CHƯƠNG 4: CÁC CẤU TRÚC LẬP TRÌNH
4.1. TỔNG QUAN
Trong các ngôn ngữ lập trình bậc cao, người ta thường sử dụng các cấu trúc lập trình cơ bản sau:
-
Cấu trúc tuần tự
-
Cấu trúc rẽ nhánh
+ Rẽ một nhánh (IF...THEN....)
+ Rẽ hai nhánh (IF...THEN...ELSE...)
+ Rẽ nhiều nhánh (CASE...OF...)
+ Lặp xác định (FOR...TO...DO)
+ Lặp không xác định
Điều kiện trước (WHILE...DO...)
Điều kiện sau (REPEAT...UNTIL...)
Sau đây ta sẽ nghiên cứu việc biểu diễn các cấu trúc lập trình trên bằng hợp ngữ trong khi các lệnh của hợp ngữ sẽ thực hiện theo cấu trúc tuần tự. Vì vậy, muốn điều khiển rẽ nhánh chương trình, chúng ta cần phải thực hiện các lệnh chuyển điều khiển.
4.1.1. Các lệnh chuyển điều khiển
4.1.1.1. Các định hướng
- Định hướng NEAR: Thông thường các lệnh điều khiển rẽ nhánh chương trình được thực hiện theo định hướng NEAR (Mặc định).
Định hướng này cho phép các lệnh chuyển điều khiển thực hiện trong khoảng 126 byte. Có nghĩa là, chỉ có thể nhảy về trước và về phía sau của lệnh 126 byte.
- Định hướng FAR: Nếu có định hướng này, chương trình dịch sẽ cho phép lệnh chuyển điều khiển rẽ nhánh ra ngoài giới hạn 126byte.
4.1.1.2. Điều kiện cho các lệnh nhảy
Các lệnh điều khiển rẽ nhánh chương trình phụ thuộc vào các trạng thái của các cờ trong thanh ghi cờ. Vì vậy, ta có thể tạo ra các điều kiện cho các lệnh này bằng một số lệnh sau:
a/ Lệnh CMP (Compare - so sánh)
Dạng lệnh: CMP toan_hang_1,toan_hang_2
ý nghĩa: Lệnh này sẽ thực hiện lấy toan_hang_1 trừ đi cho toan_hang_2 và kết quả không trả lại cho toan_hang_1. Nhưng nó sẽ tác động đến các cờ trạng thái trong thanh ghi cờ.
Ví dụ: MOV AL,3Ah ;AL=00111010
CMP AL,1Ch ;
CF= 00111000
00111010
-00011100
00011110
Như vậy, nếu xét đến các cờ trạng thái thì ta thấy lệnh trên sẽ ảnh hưởng đến cờ như sau: CF=0; PF=1; AF=1; ZF=0; SF=0; OF=0.
b/ Lệnh Test (Kiểm tra)
Dạng lệnh: TEST toan_hang_1,toan_hang_2
ý nghĩa: Lệnh này sẽ kiểm tra một bit nào đó của toan_hang_1 với các bit 1 tương ứng ở toan_hang_2.
Ví dụ: TEST AL,1 ;kiểm tra bit0 của AL xem bit này có bằng 1 hay không. Nếu giá trị của AL là một số lẻ thì bit0=1.
4.1.1.3. Các lệnh điều khiển rẽ nhánh
Về cơ bản, chúng ta có thể xét đến một số lệnh điều khiển rẽ nhánh đã nghiên cứu ở chương 1 phần 1.
Ví dụ, xét lệnh JE. Lệnh này phụ thuộc vào cờ ZF. Nếu ZF=1 thì lệnh JE mới có thể thực hiện được. Song, trên thực tế, khi xét đến điều kiện thực hiện các lệnh nhảy, ta chỉ cần quan tâm đến ý nghĩa của các từ viết tắt cho từng loại lệnh nhảy. Các điều kiện đó thể hiện như: A - Above; B -Bellow; C - Carry; E - Equal; G - Greater; L - Less; N - Not; Z - Zero... nhưng cũng có thể kết hợp với nhau để có các ý nghĩa khác nhau như: NLE; NGE; NL; LE; NG; GE; NA; NB; NAE; NBE; AE; BE
4.2. CẤU TRÚC TUẦN TỰ
Cấu trúc tuần tự là một cấu trúc mà trong đó các mã lệnh hợp ngữ được thực hiện các công việc theo trình tự hết lệnh này đến lệnh khác.
Ngữ pháp:
Lệnh_1
Lệnh_2
...........
Lệnh_n
Ví dụ: Viết một đoạn chương trình thực hiện nhập vào một kí tự từ bàn phím, sau đó in ra màn hình kí tự đó tại dòng tiếp theo.
Giải:
MOV AH,1
INT 21h
MOV AH,2
MOV DL,13
INT 21h
MOV DL,10
INT 21h
MOV DL,AL
INT 21h
4.3. CẤU TRÚC RẼ NHÁNH
4.3.1. Cấu trúc IF...THEN...
Đây là cấu trúc điều khiển rẽ nhánh chương trình với việc kiểm tra điều kiện. Nếu điều kiện thoả mãn thì thực hiện công việc. Nếu điều kiện không thoả mãn thì bỏ qua công việc này.
Ngữ pháp:
IF điều_kiện THEN công_việc
Ví dụ: Viết một đoạn chương trình thực hiện nhập vào một kí tự. Nếu là kí tự 'A' thì hiển thị tại dòng tiếp theo.
Giải:
MOV AH,1 ;Nhap vao tu ban phim mot ki tu
INT 21h ;ki tu do nam trong AL
CMP AL,41h
JNE ketthuc
PUSH AX ;Cat tam ki tu nay vao ngan xep
MOV Ah,2 ;Dua con tro
MOV DL,13 ;xuong dong tiep theo
INT 21h
MOV DL,10 ;ve ve dau dong
INT 21h
POP DX ;Lay ki tu ra va dua truc tiep vao DL
INT 21h ;In ra man hinh
Ketthuc:
MOV AH,4Ch
INT 21h
Đoạn chương trình trên sẽ thực hiện cho phép người sử dụng nhập vào từ bàn phím một kí tự. Sau đó, so sánh với mã ASCII của 'A'. Nếu không bằng thì sẽ thực hiện các lệnh sau lệnh "JNE ketthuc" rồi mới kết thúc. Nếu không, máy sẽ bỏ qua các lệnh đó và kết thúc chương trình bằng hàm ngắt 4Ch của ngắt 21h.
4.3.2. Cấu trúc IF...THEN...ELSE
Trong thực tế, chúng ta thường đưa ra một điều kiện nào đó. Nếu trường hợp thoả mãn thì sẽ thực hiện một công việc nào đó. Ngược lại, sẽ không thực hiện một công việc khác.
Ngữ pháp:
IF điều_kiện THEN
công_việc_1
ELSE
công_việc_2
END_IF
Ví dụ: Viết 1 đoạn chương trình hợp ngữ thực hiện nhập vào từ bàn phím một kí tự. Nếu kí tự nhập vào có mã ASCII nhỏ hơn mã ASCII của số 1 thì đưa ra màn hình thông báo "Kí tự này đứng trước '1' trong bảng mã", ngược lại, đưa ra màn hình thông báo "Kí tự này đứng sau '1' trong bảng mã"
Giải: Đoạn chương trình được thể hiện như sau:
* Giả thiết: thông báo "Kí tự này đứng trước '1' trong bảng mã" được lưu trong biến truoc, thông báo "Kí tự này đứng sau '1' trong bảng mã" được lưu trong biến sau
Đoạn chương trình được viết như sau:
;Nhap ki tu tu ban phim
mov ah,1
int 21h
;Bat dau cau truc
cmp AL,'1' ;so sanh ki tu nhap vao voi '1'
JL then_
MOV AH,9
LEA DX,sau
INT 21h
JMP End_if
then_:
MOV AH,9
LEA DX,truoc
INT 21h
end_if:
4.3.3. Cấu trúc rẽ nhánh CASE...OF...
Là một cấu trúc đa nhánh. Nó kiểm tra các thanh ghi, các biến hay các giá trị riêng rẽ trong miền giá trị.
Ngữ pháp:
CASE biểu_thức
Giá_trị_1: công_việc_1
Giá_trị_2: công_việc_2
.................
Giá_trị_n: công_việc_n
END CASE
Như vậy, nếu biểu thức bằng giá trị nào, thì công việc tương ứng sẽ được thực hiện.
Ví dụ: Viết một đoạn chương trình thực hiện nhập vào một kí tự. Nếu kí tự đứng trước 'A' trong bảng mã ASCII thì đưa ra thông báo kí tự đứng trước 'A'. Nếu kí tự nhập vào là 'A' thì đưa ra thông báo chính là kí tự 'A'. Nếu đứng sau 'A' thì đưa ra thông báo kí tự đứng sau 'A'.
Giải: Giả thiết các biến truoc, dung, sau chứa nội dung là các chuỗi thông báo cần đưa ra. Ta có thể thực hiện đoạn chương trình như sau:
;Nhap vao ki tu
mov ah,1
int 21h
;CASE... OF....
CMP AL,'A'
JL L1
JE L2
JG L3
L1:
MOV AH,9
LEA DX,TRUOC
INT 21H
JMP END_
L2:
MOV AH,9
LEA DX,DUNG
INT 21H
JMP END_
L3:
MOV AH,9
LEA DX,SAU
INT 21H
END_:
4.3.4. Cấu trúc rẽ nhánh với điều kiện kép
Là một dạng cấu trúc rẽ nhánh mà trong đó, điều kiện là một sự kết hợp của hai hay nhiều điều kiện khác nhau. Điều kiện kép có hai dạng
1/ Điều kiện kết hợp AND
Là cấu trúc rẽ nhánh mà trong đó có nhiều điều kiện kết hợp. Nếu tất cả các điều kiện đều thoả mãn thì công việc sẽ được thực hiện. Ngược lại, có thể thực hiện một công việc khác hoặc không thực hiện gì.
Ví dụ: Viết một đoạn chương trình thực hiện nhập vào từ bàn phím một kí tự. Kiểm tra xem phím nhập vào có phải là chữ số không
Giải:
mov ah,1
int 21h
CMP AL,'0'
JL END_IF
CMP AL,'9'
JG END_IF
;THEN
MOV AH,9
LEA DX,SO
INT 21H
END_IF:
MOV AH,4Ch
INT 21h
2/ Điều kiện kết hợp OR
Là cấu trúc rẽ nhánh mà trong đó có nhiều điều kiện kết hợp. Nếu một trong các điều kiện đều thoả mãn thì công việc sẽ được thực hiện. Ngược lại, nếu tất cả các điều kiện không được thoả mãn thì có thể thực hiện một công việc khác hoặc không thực hiện gì.
Ví dụ: Viết một đoạn chương trình thực hiện nhập vào từ bàn phím một kí tự. Kiểm tra xem phím nhập vào có phải là 'Y' hoặc 'y' không
Giải: Giả thiết có hai biến. yeucau chứa thông báo nhập vào; dung chứa thông báo kí tự nhập vào đúng là 'y' hoặc 'Y'. Đoạn chương trình sẽ được viết ra như sau:
MOV AH,9
LEA DX,yeucau
INT 21h
mov ah,1
int 21h
CMP AL,'Y'
JE THEN_
CMP AL,'y'
JE THEN_
JMP END_IF
THEN_:
MOV AH,9
LEA DX,DUNG
INT 21H
END_IF:
MOV AH,4Ch
INT 21h
4.4. CẤU TRÚC LẶP
4.4.1. Cấu trúc FOR...TO....DO....
Đây là một dạng cấu trúc lặp với số lần lặp đã được xác định.
Ngữ pháp:
FOR số_lần_lặp DO công_việc
Đầu tiên, gán cho thanh ghi đếm CX một giá trị bằng số lần lặp. Sau đó, thực hiện công việc.
Sau mỗi lần lặp, giảm giá trị trong thanh ghi CX đi 1 đơn vị và kiểm tra nó với 0. Nếu chưa bằng 0 thì tiếp tục thực hiện công viêc... cho tới khi CX=0.
Trong tập lệnh của bộ vi xử lý 8086 tồn tại một lệnh sử dụng phù hợp trong cấu trúc này. Đó là lệnh LOOP.
Lệnh này tự động giảm thanh ghi CX 1 đơn vị và sau đó so sánh CX với 0.
Ví dụ: Viết một đoạn chương thực hiện nhập vào từ bàn phím một kí tự. Sau đó cho hiển thị nó 200 lần trên màn hình
Giải:
MOV AH,9
LEA DX,YEUCAU
INT 21H
MOV CX,200
MOV AH,1
INT 21H
PUSH AX
MOV AH,2
MOV DL,13
INT 21H
MOV DL,10
INT 21H
POP AX
MOV AH,2
FOR_:
MOV DL,AL
INT 21H
LOOP FOR_
4.4.2. Cấu trúc WHILE...DO....
Là một cấu trúc lặp phụ thuộc vào một điều kiện.
Ngữ pháp:
WHILE điều_kiện DO công_việc
Công_việc sẽ được thực hiện cho đến khi điều_kiện trở nên sai
Ví dụ: Viết một đoạn chương trình thực hiện đếm số kí tự nhập vào từ bàn phím
Giải:
XOR CX,CX
MOV AH,1
WHILE_:
INT 21H
CMP AL,13
JE END_WHILE
INC CX
JMP WHILE_
END_WHILE:
MOV AH,4CH
INT 21H
4.4.3. Cấu trúc REPEAT...UNTIL....
Ngữ pháp:
REPEAT
cong_việc
UNTIL điều_kiện
Đây là cấu trúc lặp mà trong đó công_việc thực hiện trước, sau đó mới kiểm tra điều_kiện. Nếu điều_kiện đúng thì kết thúc quá trình lặp. Ngược lại, nếu điều_kiện vẫn còn sai thì quay trở lại thực hiện công_việc...
Ví dụ: Viết một đoạn chương trình thực hiện nhập vào từ bàn phím một chuỗi kí tự kết thúc bằng việc nhấn phím ENTER
Giải:
MOV AH,9
LEA DX,YEUCAU
INT 21H
REPEAT_:
MOV AH,1
INT 21H
CMP AL,13
JNE REPEAT_
MOV AH,4Ch
INT 21h
4.5. CẤU TRÚC CHƯƠNG TRÌNH CON
Nhằm mục đích làm cho chương trình ngắn gọn và dễ hiểu, thông thường người ta thực hiện chia nhỏ chương trình thành các Module khác nhau, mỗii Module có thể thực hiện một hoặc một khèi công việc nhất định. Mỗi một Module đó được gọi là một chương trình con.
Trong lập trình hợp ngữ thông thường người ta chỉ sử dụng một loại chương trình con thủ tục. Cấu trúc của chương trình con loại này được thực hiện như sau:
4.5.1. Cấu trúc của chương trình con
1/ Cấu trúc:
PROC [kiểu]
;Thân chương trình con
;....................................
RET
ENDP
Trong đó:
+ Tên ctc: Là tên Chương trình con m người sử dụng tự đặt theo qui định đặt tên của ASSEMBLY
+ PROC, ENDP: Các lệnh giả được thực hiện để khai báo bắt đầu và kết thúc chương trình con.
+ kiểu: có thể là NEAR hoặc FAR.
- NEAR (Mặc định) có nghĩa là dòng lệnh gọi thủ tục ở cùng đoạn với thủ tục đó.
- FAR có nghĩa là dòng lệnh gọi thủ tục ở trong một đoạn khác.
2/ Ví dụ:
xoamh PROC
MOV AH,0
MOV AL,3
INT 10h
RET
xoamh ENDP
3/ Một số chú ý:
- Tránh trường hợp sau khi thực hiện xong chương trình con, nội dung các thanh ghi có thể bị thay đổi, thường người ta sử dụng lệnh PUSH và POP trong chương trình con để đưa tạm vào ngăn xếp và sau đó lấy lại cho các thanh ghi. Ví dụ trong đoạn chương trình trên, sau khi thực hiện chương trình con xong, nội dung của thanh ghi AX có thể bị thay đổi. Ta có thể viết lại như sau:
xoamh PROC
PUSH AX ; đẩy tạm AX vào ngăn xếp
MOV AH,0
MOV AL,3
INT 10h
POP AX ;lấy lại giá trị cũ từ ngăn xếp cho AX
RET ;sau đó trở về chương trình chính
xoamh ENDP
- Để người khác có thể đọc và hiểu rõ thủ tục thực hiện như thế nào thì, người lập trình phải có một đoạn giải thích như sau:
;Chức năng của thủ tục
;Vào: (lấy thông tin từ chương trình gọi)
;Ra: (Trả thông tin đã được xử lý về cho chương trình gọi)
;Cách sử dung (nếu có)
Ví dụ: Viết một thủ tục thực hiện nhân 2 số nguyên dương A và B bằng cách cộng và dịch các bit.
Thuật toán:
tich=0
Repeat
if LSB(B)=1
then
tich=tich+A
end_if
SHL A,1
SHR B,1
until B=0
Đoạn mã:
nhan PROC
;Nhan 2 so A,B bang phep dich va cong cac bit
;Vao: AX=A;BX=B
;Ra: DX=ket qua
PUSH AX ;day tam AX
PUSH BX ;va BX vao ngan xep
XOR DX,DX ;xoa thanh ghi DX chua tich
REPEAT:
;if B le
TEST BX,1 ;bit LSB cua BX bang 1?
JZ END_IF ;Khong, dich trai AX....
;then
ADD DX,AX ;tich=tich+A
END_IF:
SHL AX,1 ;dich trai AX
SHR BX,1 ;dich phai BX
;until B=0
JNZ REPEAT ;B <> 0, lap lai
POP BX ;Khoi phuc lai BX
POP AX ;va AX tu ngan xep
RET
nhan ENDP
4.5.2. Cách gọi và thực hiện một chương trình con
Sau khi đó lập được một thủ tục, người lập trình chỉ việc gọi chúng ra từ một đoạn chương trình nào đó như sau:
CALL
Việc gọi chương trình con rất đơn giản, song có một số chú ý khi ta thực hiện với chương trình con.
4.5.2.1. Chương trình con nằm trong cùng một chương trình
1/ Cách gọi.
Nếu đoạn chương trình con nằm trong cùng một chương trình, thì ta có thể gọi và thực hiện theo mẫu sau. Ví dụ:
Title ctchinh
.MODEL Small
.STACK 100h
.DATA
;khai báo dữ liệu cho chương trình
.CODE
Main PROC
MOV AX,@data
MOV DS,AX
;Các lệnh của chương trình chính
CALL ctc
;Các lệnh của chương trình chính
Main ENDP
Ctc PROC
;Các lệnh của chương trình con
RET
Ctc ENDP
END Main
2/ Ví dụ: Viết một chương trình nhập vào một kí tự, sau đó in ra ở dòng tiếp theo.
4.5.2.2. Chương trình con được soạn thảo trong một tệp khác
1/ Cách gọi.
Nếu các chương trình con được soạn thảo trong một tệp khác (ví dụ CTC.LIB), thì có thể sử dụng lệnh INCLUDE tại vị trí khai báo các chương trình con. Ví dụ:
Title ctchinh
.MODEL Small
.STACK 100h
.DATA
;khai báo dữ liệu cho chương trình
.CODE
Main PROC
MOV AX,@data
MOV DS,AX
;Các lệnh của chương trình chính
CALL ctc
;Các lệnh của chương trình chính
Main ENDP
INCLUDE ctc.lib
END Main
2/ Ví dụ: Viết một chương trình nhập vào một kí tự, sau đó in ra ở dòng tiếp theo.
4.6. MACRO
Trong lập trình với ngôn ngữ bậc cao, thông thường người ta sử dụng các chương trình con với các tham số. Song trong hợp ngữ không sử dụng được các tham số, vì các chương trình con qui định trả lại các giá trị qua ngăn xếp. Vì vậy, việc trả lại các tham số cho chương trình gọi khó khăn.
Để đáp ứng vấn đề này, người ta sử dụng một loại cấu trúc được gọi là MACRO.
4.6.1. Định nghĩa MACRO
1/ Khái niệm:
MACRO thực chất chỉ là một khối văn bản có tên. Khi trình biên dịch gặp tên đó, nó sẽ chèn khối văn bản tương ứng vào chương trình. Khối văn bản trong MACRO có thể là các lệnh, các toán tử giả hoặc lời bình...
2/ Cách định nghĩa:
MACRO
;các lệnh trong thân MACRO
ENDM
Trong đó:
- Tên MACRO là một tên do người lập trình tự đặt và phải theo đúng qui định đặt tên.
- MACRO,ENDM là các toán tử giả cho biết bắt đầu và kết thúc MACRO.
- Các tham số hình thức: có thể là 1,2,3 hoặc nhiều tham số cần thiết cho việc trả lại giá trị trong chương trình gọi. Các tham số này phải được ngăn cách nhau bởi dấu phẩy.
Ví dụ: Định nghĩa MACRO chuyển dữ liệu từ một biến kiểu WORD sang một biến khác kiểu WORD.
MOVW MACRO w1,w2
PUSHw2;đẩy nội dung biến w1 vào ngăn xếp
POP w1;sau đó lấy ra cho w2
ENDM
Chú ý:
- Nếu trong đoạn MACRO cần sử dụng nhãn cho các lệnh chuyển điều khiển, thì các nhãn này phải được khai báo trước bằng lệnh
LOCAL
- Nên sử dụng các lệnh PUSH và POP trước và sau khi thực hiện một MACRO
Ví dụ:
enter MACRO
LOCAL L
PUSH AX ;AX day vao ngan xep truoc khi bi thay doi
MOV AH,08H ;Nhap vao 1 ki tu
L:
INT 21H
CMP AL,13 ;ki tu la ENTER?
JNE L ;Khong, nhap lai
POP AX ;thuc hien xong, khoi phuc lai
ENDM
4.6.2. Gọi MACRO trong chương trình
1/ Cú pháp:
Sau khi đã định nghĩa MACRO, ta có thể gọi trực tiếp chúng từ chương trình hiện tại tương tự như các lệnh khác của hợp ngữ. Theo dạng sau:
trong đó:
- Tên MACRO là tên đã được khai báo trong phần định nghĩa.
- Các tham số thực sự là các tham số, các biến của chương trình gọi. Các tham số này cũng phải được ngăn cách nhau bởi dấu phẩy.
2/ Ví dụ:
Giả sử có hai biến kiểu WORD là a và b. Nếu gọi MACRO đã định nghĩa ở trên thì ta sử dụng lời gọi như sau:
MOVW a,b ;chuyen noi dung cua bien b sang cho bien a
3/ Chú ý:
- Lời gọi MACRO phải nằm trong đoạn mã của chương trình.
- Trong trường hợp các thanh ghi có thể bị thay đổi, ta có thể sử dụng ngăn xếp để chứa dữ liệu tạm thời, và sau đó có thể khôi phục lại.
4/ Bài tập: Viết một chương trình in ra màn hình các thông tin về bản thân. Sau mỗi lần hiển thị ra một thông tin, người sử dụng
Chương trình:
title ct
.MODEL Small
.STACK 100h
.DATA
hoten DB 'Ho va ten: Nguyen Thanh Toan $'
nsinh DB 'Ngay sinh: 10-10-1983 $'
que DB 'Que quan: Thanh Mien-Hai Duong $'
;Dinh nghia MACRO in chuoi ki tu ra man hinh
WRITE MACRO st
MOV AH,9
MOV DX,OFFSET st
INT 21H
ENDM
;dinh nghia MACRO nhan phim ENTER
enter MACRO
LOCAL L
MOV AH,08H
L:
INT 21H
CMP AL,13
JNE L
ENDM
;dinh nghia MACRO in chuoi tren 1 dong WRITELN MACRO STR
MOV AH,09
LEA DX,STR
INT 21H
MOV AH,02
MOV DL,13
INT 21H
MOV DL,10
INT 21H
ENDM
.CODE
main PROC
MOV AX,@DATA ;khoi tao DS
MOV DS,AX
WRITELN HOTEN ;in ra ho va ten
ENTER ;nhan enter
WRITELN NSINH ;in ra ho va ten ENTER ;nhan enter WRITELN QUE ;in ra ho va ten ENTER ;nhan enter MOV AH,4Ch ;ket thuc
INT 21h ;chuong trinh
main ENDP
END main
4.6.3. Gọi MACRO từ đoạn chương trình khác
Đôi khi người lập trình muốn sử dụng các MACRO trong nhiều chương trình khác nhau. Nhưng nếu viết chúng trong cùng một chương trình với chương trình chính thì không thuận tiện vì mỗi một chương trình ta đều phải viết lại MACRO cho chúng.
Trong lập trình với ASSEMBLY, cho phép người lập trình có thể viết các MACRO trong một tệp riêng biệt (Tệp MACRO này chỉ chứa các MACRO, không có các cấu trúc của chương trình). Sau đó có thể sử dụng các MACRO này bằng cách chèn vào văn bản chương trình chính bằng lệnh:
INCLUDE
Lệnh này có thể chèn vào bất kì vị trí nào của chương trình mà có thể định nghĩa MACRO
Ví dụ: Viết một chương trình hiển thị các thông tin về bản thân. Các MACRO được thực hiện trong một tệp nào đó.
*Tệp chứa các MACRO
LOAD_DATA MACRO
MOV AX,@DATA
MOV DS,AX
ENDM
WRITE MACRO st
MOV AH,9
MOV DX,OFFSET st
INT 21H
ENDM
enter MACRO
local L
MOV AH,08H
L:
INT 21H
CMP AL,13
JNE L
ENDM
WRITELN MACRO STR
MOV AH,09
LEA DX,STR
INT 21H
MOV AH,02
MOV DL,13
INT 21H
MOV DL,10
INT 21H
ENDM
RET_DOS MACRO
MOV AH,4Ch
INT 21H
ENDM
*Tệp chứa chương trình chính
title ct
.MODEL Small
.STACK 100h
.DATA
hoten db 'Ho va ten: Nguyen Thanh Toan $'
nsinh db 'Ngay sinh: 10-10-1983 $'
que db 'Que quan: Thanh Mien - Hai Duong $'
INCLUDE macro.lib
.CODE
main PROC
LOAD_DATA
WRITELN HOTEN
ENTER
WRITELN NSINH
ENTER
WRITELN QUE
ENTER
RET_DOS
main ENDP
END main
Chia sẻ với bạn bè của bạn: |