Biểu thức là tổ hợp các toán tử và toán hạng được trình biên dịch chuyển thành một giá trị đơn lẻ.... Toán hạng đích phải là 1 thanh ghi 16bit: VD: mov bx, offset count ; BX trỏ đến
Trang 1GV: Ths Phạm Nguyên Văn
Trang 2 Lệnh model lựa chọn mô hình bộ nhớ.
Trang 3 Biểu thức là tổ hợp các toán tử và toán hạng được trình biên dịch chuyển thành một giá trị đơn lẻ.
Trang 5Toán tử Cấp Mô tả
Trang 6 OFFSET trả về vị trí của 1 nhãn và biến từ đầu
phân đoạn của nó Toán hạng đích phải là 1 thanh ghi 16bit:
VD: mov bx, offset count ; BX trỏ đến count
offset có thể được chuyển đến 1 thanh ghi chỉ mục hoặc cơ số Trong ví dụ sau, bList mặc định nằm tại offset 0000:
Trang 7 data
bList db 10h, 20h, 30h, 40h
wList dw 1000h, 2000h, 3000h
code
mov di, offset bList ; dl = 0000
mov bx, offset bList + 1 ; bx = 0001
mov si, offset wList+2 ; si = 0006
Trang 8 Toán tử SEG trả về phần phân đoạn của 1 nhãn
hoặc địa chỉ của biến Thường được dùng khi biến nằm trong 1 phân đoạn khác với phân đoạn hiện do
DS trỏ đến
VD: đẩy [push] giá trị hiện thời của DS lên stack,
ấn định DS theo phân đoạn chứa array, và sau đó phục hồi DS theo giá trị ban đầu của nó
Trang 10PTR: chạy đè lên kích cỡ ngầm định của một toán hạng
Phát biểu rõ kích cỡ của toán hạng.
Phải được kết hợp với các kiểu dữ liệu chuẩn: BYTE, SBYTE, WORD, DWORD,
SDWORD, FWORD, QWORD, TBYTE.
mov al,byte ptr count
mov ax, word ptr newVal
mov eax,dword ptr listPointer
Trang 11 Do kích cỡ của toán hạng không được rõ ràng xét theo ngữ cảnh 1 lệnh VD:
inc [bx] ; toán hạng gián tiếp
báo lỗi do không biết bx chứa byte hay word
inc byte ptr [bx]: xác định rõ kích cỡ của toán hạng
là byte
Có thể chạy đè kích cỡ ngầm định của toán hạng
Trang 12Vd: ta có từ kép 32bit, muốn nạp từ cao vào
DX, từ thấp vào AX:
.data
val32 dd ?
.code
mov dx, val32+2 ; có từ cao (error)
Sửa lại:
mov dx, word ptr val32+2 ; DX = 5678h
Trang 13LABEL: chèn 1 nhãn và gán cho nó 1 thuộc
Trang 14EVEN và EVENDATA: căn thẳng hàng lệnh
kế tiếp trong đoạn mã theo offset 16bit đều.
Vd: 1 lệnh NOP 1-byte (90h) được chèn vào
mã đã biên dịch nơi even xuất hiện Lệnh tiếp theo nằm tại 0006:
Trang 15 Tương tự với evendata, chèn 1 byte rỗng (0) vào trước array:
0000 data
0000 str1 db 3 dup(‘X’)
0003 evendata
0004 array dw 10 dup(0FFFFh)
Trang 16Toán tử SHORT:
thường sử dụng với JMP khi thực hiện nhảy ngắn
khoảng <= 127 byte từ vị trí hiện thời Điều này giúp trình biên dịch thực hiện 1 lệnh nhảy ngắn 1 byte
thay vì 1 lệnh nhảy gần 2 byte.
Toán tử TYPE: trả về kích cỡ của 1 thành phần đơn lẻ trong 1 biến, tính theo byte.
VD: biến 8bit trả về kiểu 1, biến 32bit trả về kiểu 4, mảng byte trả về 1, mảng 16bit trả về 2 Kiểu 1 nhãn gần là FFFFh, kiểu 1 nhãn xa là FFFEh.
Trang 17 L1: mov ax,type var1 ;ax = 0001
mov ax,type var2 ;ax = 0002
mov ax,type var3 ;ax = 0004
mov ax,type var4 ;ax = 0001
mov ax,type msg ;ax = 0001
mov ax,type L1 ;ax = FFFF
Trang 18 Toán tử length: đếm số lượng các thành phần riêng
lẻ trong 1 biến được định nghĩa bằng dup
Nếu không dùng dup, length = 1
Nếu dùng dup lồng ghép, chỉ toán tử phía ngoài mới được đếm
Trang 19 data
val1 dw 1000h
val2 db 10,20,30
array dw 32 dup(0)
array2 dw 5 dup(3 dup(0))
message db ‘File not found’,0
code
mov ax,length val1 ; = 1
mov ax,length val2 ; = 1
mov ax,length array ; = 32
Trang 20 Toán tử SIZE: = length * type của 1 biến.
intArray dw 32 dup(0) ; SIZE = 64
Trang 21 Định nghĩa 1 dãy các hằng và gán giá trị nguyên cho từng hằng Tất cả các ký hiệu đều được định nghĩa trên một dòng:
name enum [, symbol1[, symbol2,…[, symbol-n] ] ]
VD:
driveStatus enum ready, busy, offline
Ngầm định: ready = 0, busy = 1, offline = 2
Trang 22 Có thể sử dụng {} để định nghĩa enum trong nhiều dòng:
mov al, blue ; ok
mov ax, blue ; lỗi
Trang 23Cách dùng: giả sử đã định nghĩa ColorType trong chương trình ngay trước lệnh data:
Trang 24Giá trị tường minh: mỗi hằng có thể tuỳ ý được gán một giá trị giữa 0 và 0FFFFh (nếu giá trị 0,
Trang 25Nếu giá trị tường minh đã gán cho các hằng vượt quá bộ nhớ 1 byte, kiểu enum sẽ tự
chuyển sang word:
StatusVals enum {
normal = 1000h, overheat = 2000h, highSpeed = 3000h }
code
mov al, overheat ; lỗi
Trang 26 ASM so sánh 2 số bằng cách thực hiện 1 phép toán số học hoặc logic trên 2 số đó và căn cứ vào thanh ghi cờ để đưa ra kết luận
Để làm việc này có thể dùng lệnh CMP và TEST.
Trang 27 Bản chất của lệnh TEST là lệnh AND <đích>,
Trang 28 Được sử dụng trong các trường hợp chuyển giao điều khiển hoặc rẽ nhánh.
Chuyển giao không điều kiện: chương trình rẽ nhánh đến 1 vị trí trong tất cả các trường hợp.
Chuyển giao có điều kiện: chương trình rẽ nhánh nếu 1
đk nhất định = true.
Trang 29 Là lệnh nhảy không điều kiện:
JMP <đích>
JMP SHORT <đích>: khi đó mã lệnh lưu 1 byte khoảng cách (offset) giữa vị trí hiện tại và vị trí cần nhảy Kiểu này chỉ nhảy trong phạm vi -128~+127 byte so với vị trí hiện tại.
VD:
JMP SHORT Calculate
JMP <đích>: khi đó trong mã lệnh lưu 2 byte khoảng cách giữa
vị trí cần nhảy và vị trí hiện tại Kiểu này nhảy đến bất kỳ chỗ nào.
VD:
JMP Thoat
Trang 30 JMP FAR PTR <đích>: nhảy tùy ý trong phạm vi segment.
VD:
JMP FAR PTR Calculate
JMP <con trỏ 2 byte>: mã lệnh lưu địa chỉ của 1 ô nhớ Khi thực hiện, IP sẽ được gán bằng giá trị lưu tại địa chỉ này Có thể kết hợp để định vị chỉ số.
Trang 31 JMP <con trỏ 4 byte>: tương tự trường hợp trên nhưng con trỏ gồm cả segment và offset Chỉ khác ở khai báo con trỏ.
Trang 32 Các lệnh nhảy có điều kiện bắt đầu bằng chữ J, sau đó
là chữ cái hiển thị điều kiện.
Trang 33Một số lệnh nhảy thường dùng:
JE, JZ: nhảy nếu bằng.
JA (nhảy nếu lớn hơn, không dấu), JG (nhảy nếu lớn hơn,
có dấu), JB (nhảy nếu nhỏ hơn, không dấu), JL (nhảy nếu nhỏ hơn, có dấu)
JAE (nhảy nếu lớn hơn hoặc bằng, không dấu), JGE
(nhảy nếu lớn hơn hoặc bằng, có dấu), JBE (nhảy nếu <=, không dấu), JLE (nhảy nếu <=, có dấu)
JNE, JNZ (nhảy nếu không bằng)
VD: nếu al là số nguyên không dấu thì đoạn chương trình trên như sau:
mov ah, al
cmp ah, 1
jae Greater
Trang 34 Lặp một khối lệnh cụ thể Thanh CX được sử dụng làm bộ đếm.
Cú pháp:
Loop <nhãn>: tự động giảm CX 1 đơn vị, sau đó kiểm tra xem CX có = 0 hay không, nếu không bằng thì nhảy đến <nhãn>.
Loopz <nhãn>: tự động giảm CX 1 đơn vị, kiểm tra
xem CX = 0 hoặc cờ ZF có bật không, nếu cả 2 điều này không xảy ra thì nhảy đến nhãn.
Trang 35 Thay đổi bộ đếm trong vòng lặp.