dùng trong một số lãnh vực hẹp, chủ yếu để giao tiếp trực tiếp với phần cứng hoặc
xử lý các vấn đề liên quan đến tốc độ cao điển hình như các trình điều khiển thiết bị,
các hệ thống nhúng cấp thấp và các ứng dụng thời gian thực..
2.4.2 Các bước khi lập trình
Lập trình trên phần mềm emu8086
- Bước 1: Mở chương trình emu8086, chọn file \ new Với các lựa chọn:
New com template, new exe template, new bin template, new boot
template.
- Bước 2: Viết mã nguồn
- Bước 3: dịch và gỡ rối [bấm F5]
- Bước 4: tạo file tự chạy: assembler \ Compile
Dịch, liên kết, chạy và chẩn lỗi chương trình từ dấu nhắc DOS:
Cần có các file: tasm.exe [dịch], tlink.exe [liên kết], td.exe [chẩn lỗi]. Các bước như
sau:
B1. Thiết lập đường dẫn
path = %path%;
B2. Biên dịch từ file .ASM sang file .OBJ
Tasm .ASM
B3. Biên dịch từ file .OBJ sang file .EXE
Tlink .OBJ
B4: chạy chương trình:
.EXE
B5: chẩn lỗi [nếu cần thiết]
Td .EXE
Để tự động hóa, ta có thể tạo file .BAT chứa các lệnh trên.
Ví dụ:
Tạo file RunASM.bat trong cùng thư mục với tập tin .ASM với nội dung như
sau :
tasm %1
tlink %1
%1
[%1 là lấy tham số thứ nhất trong command line]
Sau đó để biên dịch, liên kết và thực thi chương trình hello.ASM ta chỉ cần
gõ :
RunASM hello
Chương trình emu8086:
Chương trình emu8086 là chương trình lập trình mơ phỏng cho 8086 [tương
thích Intel và AMD] bao gồm bộ dịch ASM và giáo trình [tiếng anh] cho người mới
bắt đầu. Chương trình có thể chạy hết hoặc chạy từng bước, ta có thể nhìn thấy các
thanh ghi, bộ nhớ, stack, biến,
Hình 2-5. Emu8086 - Mơi trường soạn thảo
Hình 2-6. Emu8086 - Giá trị các cờ và màn hình hiển thị
Hình 2-7. Emu8086 - Màn hình Debug chương trình
2.4.3 Cấu trúc chung của chương trình hợp ngữ
2.4.3.1 Cấu trúc của một lệnh hợp ngữ
Tham khảo [9]
Một dòng lệnh trong chương trình hợp ngữ gồm có các trường
sau:
Tên Lệnh
Tốn hạng Chú thích
A:
Mov
AH, 10h
; Đưa giá trị 10h vào thanh ghi AH
Trường tên chứa nhãn, tên biến hay tên thủ tục. Các tên nhãn có thể chứa
tối đa 31 ký tự, không chứa ký tự trắng [space] và không được bắt đầu bằng số. Các
nhãn được kết thúc bằng dấu ':'.
Trường lệnh chứa các lệnh sẽ thực hiện. Các lệnh này có thể là các lệnh
thật [MOV] hay các lệnh giả [PROC]. Các lệnh thật sẽ được dịch ra mã máy.
Trường toán hạng chứa các toán hạng cần thiết cho lệnh [AH,10h].
Trường chú thích phải được bắt đầu bằng dấu ';'. Trường này chỉ dùng cho
người lập trình để ghi các lời giải thích cho chương trình. Chương trình dịch sẽ bỏ
qua các tất cả những gì nằm phía sau dấu ;
. Cấu trúc thơng thường của một chương trình hợp ngữ dạng file *.exe
Chương trình hợp ngữ
Kiểu kích thước bộ nhớ ; Khai báo quy mô sử dụng bộ nhớ
Kích thước
; Khai báo dung lượng đoạn stack
; Khai báo đoạn dữ liệu
TITLE
.MODEL
.STACK
.DATA
msg DB 'Hello$'
.CODE; Khai báo đoạn mã main PROC
CALL
; Gọi chương trình con
Subname
main ENDP
Subname PROC; Định nghĩa chương trình con
RET
Subname ENDP
END main
Quy mơ sử dụng bộ nhớ:
Thơng thường, các ứng dụng đơn giản chỉ đòi hỏi mã chương trình khơng q
64 KB và dữ liệu cũng không lớn hơn 64 KB nên ta sử dụng ở dạng Small:
.MODEL SMALL
CPU 8086 có thể truy nhập tối đa 1MB bộ nhớ RAM. Dung lượng này là
thừa để sử dụng cho bất kỳ loại máy tính nào.
Bản đồ bộ nhớ của máy tính
IBM PC
Địa chỉ vật lý của vùng nhớ
[HEX]
00000 - 00400
00400 - 00500
00500 - A0000
A0000 - B1000
B1000 - B8000
Giải thích vắn tắt
Vector ngắt. Bộ mo phỏng sẽ load file này:
c:\emu8086\INT_VECT tại địa chỉ vật lý 000000
Vùng thông tin hệ thống.
Một vùng nhớ tự do. Mỗi khối là 654,080 byte. Tại đây có
thể load chương trình
Vùng nhớ màn hình cho VGA, monochrome, và cho các bộ
điều hợp khác
Dự trữ
Bản đồ bộ nhớ của máy tính
IBM PC
Địa chỉ vật lý của vùng nhớ
[HEX]
Giải thích vắn tắt
32kb nhớ màn hình cho chế độ đồ họa màu [CGA]. Bộ mô
phỏng sử dụng vùng nhớ này để lưu 8 trang vùng nhớ màn
hình. Màn hình mơ phỏng có thể thay đổi kích thước, nên
bộ nhớ tối thiểu được yêu cầu cho mỗi trang, mặc dù bộ
mô phỏng luôn luôn sử dụng 1000h [4096 byte] cho mỗi
trang [xem ngắt 10h, AH=05h]
Dự trữ
ROM BIOS và mở rộng. Bộ mô phỏng tải file BIOS_ROM
tại địa chỉ vật lý 0F4000h. Địa chỉ của bảng vector ngắt chỉ
tới vùng nhớ này để tạo hàm ngắt mô phỏng.
B8000 - C0000
C0000 - F4000
F4000 - 10FFEF
Bảng vector ngắt [vùng nhớ từ 00000h đến 00400h]
Số hiệu
Địa chỉ
Địa chỉ của chương trình con BIOS
ngắt [HEX]
vector ngắt
[address of BIOS sub-program ]
00
00x4 = 00 F400:0170 CPU tạo, lỗi chia
04
04x4 = 10 F400:0180 - CPU tạo, phát hiện INTO tràn
10
10x4 = 40 F400:0190 Hàm video
11
11x4 = 44 F400:01D0 Nhận danh sách thiết bị BIOS
12
12x4 = 48 F400:01A0 Nhận kích thước bộ nhớ
13
13x4 = 4C F400:01B0 - Các hàm về đĩa
15
15x4 = 54 F400:01E0 Các hàm BIOS
16
16x4 = 58 F400:01C0 - Các hàm bàn phím
17
17x4 = 5C F400:0400 Máy in
19
19x4 = 64 FFFF:0000 Khởi động lại
1A
1Ax4 = 68 F400:0160 Hàm thời gian
1E
1Ex4 = 78 F400:AFC7 vector tham số đĩa
20
20x4 = 80 F400:0150 Hàm DOS: Kết thúc chương trình
21
21x4 = 84 F400:0200 Các hàm của DOS
33
33x4 = CC F400:0300 Các hàm chuột
Các hàm khác
??x4 = ??
F400:0100 Các ngắt mặc định
Địa chỉ [HEX]
0040h:0010
Vùng thông tin hệ thống [Bộ nhớ từ 00400h to 00500h]
Kích thước Giải thích
Danh sách thiết bị BIOS
WORD
Trường bit BIOS tìm thấy phần cứng được cài:
bit[s]
Giải thích
15-14 Số thiết bị song song
13 Dự trữ
Bản đồ bộ nhớ của máy tính
IBM PC
Địa chỉ vật lý của vùng nhớ
[HEX]
0040h:0013
0040h:004A
0040h:004E
0040h:0050
0040h:0062
0040h:0084
Giải thích vắn tắt
12 Cổng game được cài
11-9 Số thiết bị nối tiếp
8
Dự trữ
7.6 Số đĩa mềm [trừ 1]:
00 Đĩa mềm đơn;
01 Hai dĩa mềm;
10 Ba đĩa mềm;
11 Bốn đĩa mềm;
5.4 Khởi tạo chế độ Video:
1 EGA,VGA,PGA, hoặc on-board video BIOS
khác;
2 40x25 CGA màu.
10 80x25 CGA màu [Mô phỏng mặc định].
11 80x25 đen trắng.
3
Dữ trữ.
2
Chuột PS/2.
1
Bộ xử lý toán học;
0
Được cài khi khởi động từ đĩa mềm.
kilobytes bắt đầu vùng nhớ liên tiếp tại địa chỉ 00000h
WORD
từ này cũng được trả về AX bởi INT 12h
giá trị này được đặt là 0280h [640KB]
Số cột trên màn hình.
WORD
Mặc định là 0032h [50 cột]
Địa chỉ bắt đầu trang màn hình hiện hành trong bộ nhớ màn
WORD
hình [sau 0B800:0000]
Giá trị mặc định: 0000h
Bao gồm vị trí hàng và cột cho con trỏ trong mỗi của tám
8 WORD
trang nhớ màn hình.
Giá trị mặc định: 00h [cho tất cả 8 từ [words]
Số trang màn hình hiện hành
BYTE
Mặc định: 00h [trang đầu tiên]
Hàng trên màn hình trừ 1
BYTE
Giá trị mặc định: 13h [19+1=20 cột]
Bảng 2-4. Bản đồ bộ nhớ, địa chỉ ngắt của 8086
Khai báo kích thước stack:
Khai báo stack dùng để dành ra một vùng nhớ dùng làm stack [chủ yếu phục vụ
cho chương trình con], thơng thường ta chọn khoảng 256 byte là đủ để sử dụng [nếu
khơng khai báo thì chương trình dịch tự động cho kích thước stack là 1 KB]:
.STACK 256
Khai báo đoạn dữ liệu:
Đoạn dữ liệu dùng để chứa các biến và hằng sử dụng trong chương trình.
Khai báo đoạn mã:
Đoạn mã dùng chứa các mã lệnh của chương trình. Đoạn mã bắt đầu bằng một
chương trình chính và có thể có các lệnh gọi chương trình con [CALL].
Một chương trình chính hay chương trình con bắt đầu bằng lệnh PROC và kết
thúc bằng lệnh ENDP [đây là các lệnh giả của chương trình dịch]. Trong chương
trình con, ta sử dụng thêm lệnh RET để trả về địa chỉ lệnh trước khi gọi chương
trình con.
Chương trình được kết thúc bằng lệnh END trong đó tên chương trình phía sau
lệnh END sẽ xác định đó là chương trình chính. Nếu sau lệnh END khơng chỉ ra
chương trình nào cả thì sẽ lấy chương trình con ở đàu đoạn mã làm chương trình
chính.
Ví dụ: Chương trình sau in ra màn hình dòng chữ Hello !
.modelsmall 100h
.stack
.data DBHello !$ ; khai báo xâu kí tự cần in
s
.codemovAX,@data; lấy địa chỉ data segment ghi vào DS movDS,AX; Vì model small, đây cũng là địa chỉ
; segment của xâu s. ; xuất chuỗi:
mov mov int mov
DX, OFFSET s AH , 9
int
21h AH, 4Ch
21h
; lấy địa chỉ offset ghi vào DX
; gọi hàm 9, ngắt 21h để in
; Thốt khỏi chương trình
end
Lưu ý:
- Mọi chương trình đều phải có đoạn CODE thốt khỏi chương trình, nếu
khơng chương trình sẽ khơng dừng khi hết chương trình của mình.
2.4.3.2 Khung chương trình dịch ra .exe
Các tập tin .EXE và .COM
DOS chỉ có thể thi hành được các tập tin dạng .COM và .EXE. Tập tin .COM
thường dùng để xây dựng cho các chương trình nhỏ còn .EXE dùng cho các chương
trình lớn.
Tập tin .EXE
Nằm trong nhiều đoạn khác nhau, kích thước thơng thường lớn hơn 64
KB.
- Có thể gọi được các chương trình con dạng near hay far.
- Tập tin .EXE chứa một header ở đầu tập tin để chứa các thông tin điều khiển cho
tập tin.
data segment
; add your data here!
pkey db "press any key to exit ...$"
ends
stack segment
dw
128 dup[0]
ends
CODE segment
start:
; set segment registers:
MOV ax, data
MOV ds, ax
MOV es, ax
; add your CODE here
lea dx, pkey
MOV ah, 9
int 21h
; output string at ds:dx
; wait for any key....
MOV ah, 1
int 21h
MOV ax, 4c00h ; exit to operating system.
int 21h
ends
END start ; set entry point and stop the assembler.
2.4.3.3 Khung chương trình dịch ra .com
- Tập tin .COM chỉ có một đoạn nên kích thước tối đa của một tập tin loại này là 64
KB.
- Tập tin .COM được nạp vào bộ nhớ và thực thi nhanh hơn tập tin .EXE nhưng chỉ
áp dụng được cho các chương trình nhỏ.
- Chỉ có thể gọi các chương trình con dạng near.
Khi thực hiện tập tin .COM, DOS định vị bộ nhớ và tạo vùng nhớ dài 256
byte ở vị trí 0000h, vùng này gọi là PSP [Program Segment Prefix], nó sẽ chứa các
thơng tin cần thiết cho DOS. Sau đó, các mã lệnh trong tập tin sẽ được nạp vào sau
PSP ở vị trí 100h và đưa giá trị 0 vào stack. Như vậy, kích thước tối đa thực sự của
tập tin .COM là 64 KB 256 byte PSP 2 byte stack.
Tất cả các thanh ghi đoạn đều chỉ đến PSP và thanh ghi con trỏ lệnh IP chỉ
đến 100h, thanh ghi SP có giá trị 0FFFEh.
; You may customize this and other start-up templates;
; The location of this template is
;c:\emu8086\inc\0_com_template.txt
CSEG
SEGMENT
org 100h
; add your CODE here
ret
; code segment starts here.
Khai báo dữ liệu
Khi khai báo dữ liệu trong chương trình, nếu sử dụng số nhị phân, ta phải dùng
thêm chữ B ở cuối, nếu sử dụng số thập lục phân thì phải dùng chữ H ở cuối. Chú ý
rằng đối với số thập lục phân, nếu bắt đầu bằng chữ A..F thì phải thêm vào số 0 ở
phía trước.
Ví dụ:
1011b ; Số nhị phân
1011 ; Số thập phân
1011d ; Số thập phân
1011h ; Số thập lục phân
Khai báo hằng, biến
Cú pháp:
D
hoặc
D dup[]
Các kiểu dữ liệu: B [1 byte], W [2 bytes], D [4 bytes]
Nếu không khởi tạo, dùng dấu hỏi ?
Ví dụ:
Khai báo trong C
Khai báo biến trong hợp ngữ
char ch;
ch DB ?
char ch = a;
ch DB a
char ch = 5;
ch DB 5
Char s[]=\nhello world!
s DB 10,13,hello world!$
int i=100;
i DW 100
long L;
L DD ?
char a[] = {1,2,3};
a DB 1,2,3
char a[100];
a DB 100 dup[?]
char a[100][50];
a DB 100 dup[50 dup[?]]
Hằng số:
Khai báo hằng số trong chương trình hợp ngữ bằng lệnh EQU.
Ví dụ:
A1
A2
EQU
EQU
02, 11
19, 81
Tốn tử trong hợp ngữ
Tốn tử số học
Trong đó bt, bt1, bt2 là các biểu thức hằng, n là số nguyên.
Toán tử logic: Bao gồm các toán tử AND, OR, NOT, XOR
Toán tử quan hệ: Các toán tử quan hệ so sánh 2 biểu thức, cho giá trị true [1] nếu
điều kiện thoả và false [0] nếu khơng thoả.
Tốn tử cung cấp thơng tin:
- Tốn tử SEG: SEG bt ; Toán tử SEG xác định địa chỉ đoạn của biểu thức bt.
bt có thể là biến, nhãn, hay các toán hạng bộ nhớ.
- Toán tử OFFSET: OFFSET bt ;Toán tử OFFSET xác định địa chỉ offset của
biểu thức bt. bt có thể là biến, nhãn, hay các toán hạng bộ nhớ.
VD: MOV AX,SEG A ; Nạp địa chỉ đoạn và địa chỉ offset
MOV DS,AX ; của biến A vào cặp thanh ghi
MOV AX,OFFSET A ; DS:AX
- Toán tử chỉ số [ ]: [index operator] Toán tử chỉ số thường dùng với toán hạng
trưc tiếp và gián tiếp.