Lệnh MOV AX, BX là một ví dụ của chế độ định địa chỉ nào

CHƯƠNG IV . LỆNH VÀ CHẾ ĐỘ ĐỊA CHỈ

I. Cấu trúc mã lệnh

Quy trình thực hiện một lệnh trong bộ vi xử lý được chia làm ba giai đoạn: Lấy lệnh [feeching], giải mã lệnh [decording] và xử lý lệnh [excution]. Những bộ VXL cổ điển 8 bit tiến hành ba giai đoạn trên một cách tuần tự. Từ các bộ VXL 16 bit trở đi, bộ VXL dùng pipeline [xen kẽ dòng lệnh] để tiết kiệm thời gian xử lý. Mã lệnh dành cho VXL được viết dưới dạng mã nhị phân. Để con người có thể lập trình và hiểu được VXL, người ta dùng hợp ngữ [assembly language] để miêu tả các lệnh máy bằng tổ hợp các ký tự gợi nhớ [mnemonic].

Một lệnh mô tả bằng mã nhị phân có thể dài từ 1 đến 6 byte. Cấu trúc chung của một mã lệnh bao gồm:

- Prefix đi trước mã lệnh.

- Mã toán [operation code] phân biệt đó là lệnh gì, ví dụ với lệnh dịch chuyển MOV có mã toán là 100010.

- Toán hạng [operand] cho biết cái gì được xử lý [nội dung của thanh ghi hay bộ nhớ].

- Địa chỉ trực tiếp [2 byte].

Nội dung của mã lệnh được quy định khá chặt chẽ. hình 4-1 dưới đây cho thấy cấu trúc nhị phân của một lệnh dịch chuyển MOV đích, nguồn dùng để chuyền dữ liệu giữa 2 thanh ghi hoặc giữa ô nhớ và thanh ghi.

1 0 0 0 1 0 Địa chỉ

phần thấp Địa chỉ

phần cao

Mã lệnh D W MOD REG M/R

Byte 1 Byte 2 Byte 3 Byte 4

Hình 4-1: Cấu trúc mã lệnh

- Bit D [direction] chỉ hướng cho thanh ghi REG. D=1 chỉ dữ liệu đi đến REG; D=0 thì chỉ dữ liệu đi từ REG.

- Bit W [Word] chỉ xem thanh ghi được dùng là 8 bit hay 16 bit [1 word]. W=1 có nghĩa là thanh ghi 16 bit được dùng. Bảng 4-1 cho thấy cách mã hoá các thanh ghi trong bộ VXL:

- Hai bit MOD [mode, chế độ] và ba bit R/M [register/memory, thanh ghi/bộ nhớ] tạo ra 5 bit, dùng để chỉ chế độ địa chỉ của lệnh. Những chế độ này được quy định trong bảng 4-1. Bảng 4-2 cho thấy cách mã hoá các chế độ địa chỉ [cách tìm ra các toán hạng] bằng các bit này.

Bảng 4-1: Cách mã hoá các thanh ghi trong bộ VXL.

Thanh ghi

W=1 Thanh ghi

W=0 Mã REG Thanh ghi đoạn Mã

AX

BX

CX

DX

SP

DI

BP

SI AL

BL

CL

DL

AH

BH

CH

DH 000

011

001

010

100

111

101

110 ES

CS

SS

DS 00

01

10

11

Bảng 4-2: Phối hợp MOD và R/M để tạo ra các chế độ địa chỉ.

MOD

R/M 00 01 10 11

W=0 W=1

000 [BX] + [SI] [BX] + [SI] + d8 [BX] + [SI] + d16 AL AX

001 [BX] + [DI] [BX] + [DI] + d8 [BX] + [DI] + d16 CL CX

010 [BP] + [SI] [BP] + [SI] + d8 [BP] + [SI] + d16 DL DX

011 [BP] + [DI] [BP] + [DI] + d8 [BP] + [DI] + d16 BL BX

100 [SI] [SI] + d8 [SI] + d16 AH SP

101 [DI] [DI] + d8 [DI] + d16 CH BP

110

d16

[Địa chỉ trực tiếp] [BP] + d8 [BP] + d16 DH SI

111 [BX] [BX] + d8 [BX] + d16 BH DI

Chế độ bộ nhớ Chế độ thanh ghi

Ghi chú: - d8: disp. 8 bit, d16: disp. 16 bit.

- Các gía trị cho trong các cột 2, 3, 4 là các địa chỉ hiệu dụng [EA] sẽ được cộng với DS để tạo ra địa chỉ vật lý [riêng BP phải được cộng với SP].

Ví dụ 1: Mã hoá các lệnh: a. MOV CL,[BX]; b. MOV 0F3H[SI],CL.

a. MOV CL, [BX]

1 0 0 0 1 0 1 0 0 0 0 0 1 1 1 1

Các bit mã hoá CL; ô nhớ có địa chỉ DS:BX;

Chuyển 1 bite; Opcode. Chuyển tới thanh ghi

b. MOV 0F3H[SI], CL

1 0 0 0 1 0 0 0 0 1 0 0 1 1 0 0 1 1 1 1 0 0 1 1

Các bit mã hoá CL; ô nhớ có địa chỉ DS:SI; chuyển 1 bite;

Opcode. Chuyển từ thanh ghi; d8 = F3H.

II. Tập lệnh của bộ vi xử lý.

Mỗi bộ vi xử lý có một tập lệnh xác định, các bộ vi xử lý thế hệ sau thường có tập lệnh được bổ sung, mở rộng hơn so với các bộ vi xử lý thế hệ trước nó, điều đó có nghĩa các bộ vi xử lý thế hệ sau có thể chạy được các chương trình viết cho các bộ vi xử lý trước. Nhưng ngược lại thì không hoàn toàn đúng.

Như đã nói trên đây, chúng ta lấy bộ vi xử lý Intel 8088 làm cơ sở để nghiên cứu những vấn đề kỹ thuật của các bộ vi xử lý khác. Vì vậy ở đây chúng ta cũng sẽ nghiên cứu tập lệnh của chính bộ vi xử lý này.

Tập lệnh của 8086/8088 gồm hơn 100 ký hiệu gợi nhớ [mnemonic] của lệnh ngôn ngữ assembler cơ sở, để quy định cho bộ vi xử lý phải làm gì. Mỗi lệnh cơ sở có thể có nhiều biến cách. Ví dụ có tới 28 biến cách khác nhau cho lệnh dịch chuyển cơ sở [MOV] ... . Tuy nhiên trong chương trình môn học này, chúng ta chỉ xem xét một số lệnh cần thiết theo mục tiêu của môn học. Các lệnh mà chúng ta sẽ nghiên cứu được chia làm 6 nhóm:

1. Nhóm lệnh truyền dữ liệu.

2. Nhóm lệnh số học.

3. Nhóm lệnh logic.

4. Nhóm lệnh so sánh.

5. Nhóm lệnh điều khiển chương trình.

6. Các lệnh đặc biệt.

II.1 . Nhóm lệnh truyền dữ liệu [không ảnh hưởng đến các cờ].

MOV lệnh di chuyển dữ lệu cơ bản . Lệnh này cóthể sử dụng để di chuyển byte [8 bit] hoặc lời [16 bit] của dữ liệu. Cấu trúc lệnh :

MOV đích, nguồn.

Trong đó toán hạng đích và gốc có thể tìm theo các địa chỉ khác nhau, nhưng phải có cùng độ dài và không được phép đồng thời là 2 ô nhớ hoặc 2 thanh ghi đoạn.

Các ví dụ cho trong bảng 4-3:

Bảng 4-3 các ví dụ về lệnh MOV.

Đích Nguồn Ví dụ Giải thích

1 Bộ nhớ

2 Thanh ghi

3 Thanh ghi

4 Thanh ghi

Thanh ghi

Bộ nhớ

Thanh ghi

Tức thời MOV 100H, AX

MOV AX, MEM1

MOV AX, BX

MOV AX, 0FFFFH - chuyển nôi dung trong AX vào vị trí nhớ 100H.

- Chuyển nội dung trong vị trí nhớ do nhãn MEM1 chỉ ra vào thanh ghi AX.

- Chuyển nội dung trong BX vào thanh ghi AX.

- Chuyển giá trị hằng số FFFFH vào thanh ghi AX; số 0 ở đầu được dùng để phân biệt và chỉ rõ FFFFH là một giá trị hằng chứ không phải là một nhãn.

XCHG -exchange two operands [hoán đổi nội dung 2 toán hạng].

Viết lệnh: XCHG Đích, Nguồn

Trong đó toán hạng đích và nguồn có thể tìm được theo các chế độ địa chỉ khác nhau, nhưng phải có cùng độ dài và không được phép đồng thời là 2 ô nhớvà cũng không được là thanh ghi đoạn.

Ví dụ:

XCHG AH, AL ; tráo nội dung AH và AL.

XCHG AL, [BX] ; tráo nội dung AL với ô nhớ có địa chỉ DS:BX.

IN- Input data from a port [Đọc dữ liệu từ cổng vào thanh Acc]

Viết lệnh: IN Acc, Port

Port là địa chỉ 8 bit của cổng, nó có thể có giá trị trong khoảng 00H..FFH.

Nếu Acc là AL thì dữ liệu 8 bit được đưa vào từ cổng Port.

Nếu Acc là AX thì dữ liệu 16 bit được đưa vào từ cổng Port và Port+1.

Có thể biểu diễn địa chỉ cổng thông qua thanh ghi DX và như vậy địa chỉ cổng được địa chỉ hoá linh hoạt hơn. Lúc này địa chỉ cổng nằm trong dải 0000H..FFFFH và lệnh được viết như sau:

IN Acc, DX

Trong đó DX phải được gán từ trước giá trị ứng với cổng.

OUT- Output a byte or word to a port [ Đưa dữ liệu ra cổng từ Acc].

Viết lệnh: OUT Port, Acc

Nếu Acc là AL thì dữ liệu 8 bit được đưa ra cổng Por

Nếu Acc là AH thì dữ liệu 16 bit được đưa ra cổng Port và cổng Port+1.

Tương tự với lệnh IN, ở đây cũng có thể dùng thanh ghi DX để chứa địa chỉ cổng. Khi đó lệnh được viết như sau:

OUT DX, Acc.

Thanh ghi DX phải được nạp địa chỉ cổng từ trước.

LEA [load effective address]. Lệnh nạp địa chỉ hiệu dụng vào thanh ghi, nó không di chuyển nội dung chứa trong địa chỉ đó. Đây là lệnh để tính địa chỉ lệch hoặc địa chỉ của ô nhớ chọn làm gốc rồi nạp vào thanh ghi đã chọn.

Viết lệnh: LEA Đích, nguồn.

trong đó :

- Đích thường là một trong các thanh ghi BX, CX, DX, BP, SI, DI.

- Nguồn là tên biến trong đoạn DS được chỉ rõ trong lệnh hoặc ô nhớ cụ thể.

Ví dụ:

LEA DX, MSG ; Nạp địa chỉ lệch của bản tin MSG vào DX.

LEA CX, [BX] [DI] ; Nạp vào CX địa chỉ hiệu dụng do

; BX và DI chỉ ra: EA=BX+DI.

PUSH/POP Thanh ghi ngăn xếp là nơi rất thuận tiện để cất giữ tạm dữ liệu và các toán hạng cần nhớ của chương trình. Ví dụ, một chương trình có thể muốn cất lại các nội dung trong thanh ghi AX để dùng trong một số thao tác sau này. Để thực hiện nhiệm vụ đó có thể dùng các lệnh PUSH và POP.

- PUSH Cất dữ liệu vào ngăn xếp.

Viết lệnh: PUSH nguồn

Mô tả: SP  SP - 2

Nguồn  {SP}.

trong đó toán hạng gốc có thể tìm được theo các chế độ địa chỉ khác nhau: có thể là các thanh ghi đa năng, thanh ghi đoạn hoặc ô nhớ. Lệnh này thường dùng với lệnh POP như một cặp đối ngẫu để xử lý các dữ liệu và trạng thái của chuương trình chính khi vào/ra chương trình con.

Ví dụ:

PUSH BX ; cất BX vào ngăn xếp, tại vị trí do SP chỉ ra.

PUSH Table[BX] ; cất 2 byte của vùng dữ liệu DS

; có địa chỉ đầu tại [Table+BX].

- POP Lấy dữ liệu từ ngăn xếp.

Viết lệnh: POP Đích

Mô tả: Đích  {SP}.

SP  SP + 2

trong đó toán hạng gốc có thể tìm được theo các chế độ địa chỉ khác nhau: có thể là các thanh ghi đa năng, thanh ghi đoạn [nhưng không được là thanh ghi đoạ mã CS] hoặc ô nhớ. Dữ liệu để tại ngăn xếp không thay đổi. Giá trị của SS không thay đổi. Ví dụ:

POP DX ; lấy 2 byte từ đỉnh ngăn xếp, đưa vào DX.

PUSH Table[BX] ; lấy 2 byte ở đỉnh ngăn xếp rồi để tại vùng DS

; có địa chỉ đầu tại [Table+BX].

PUSHF/POPF Các nội dung của thanh ghi cờ có thể được gửi vào hay lấy ra khỏi ngăn xếp bằng các lệnh PUSPF và POPF.

- PUSHF Cất nội dung thanh ghi cờ vào ngăn xếp.

Viết lệnh: PUSHF

Mô tả: SP  SP - 2

RF  {SP}.

Dữ liệu để tại thanh ghi cờ không thay đổi. SS không thay đổi.

- POPF Lấy 1 từ, từ đỉnh ngăn xếp đưa vào thanh ghi cờ.

Viết lệnh: POPF

Mô tả: RF  {SP}.

SP  SP + 2

Sau lệnh này dữ liệu để tại ngăn xếp không thay đổi. SS không thay đổi.

II.2. Nhóm lệnh số học [là nhóm lệnh có ảnh hưởng đến cờ].

Các lệnh số học bao gồm bốn phép tính số học cơ bản là cộng, trừ , nhân, chia và đảo dấu toán hạng.

ADD/SUB Dạng tổng quát của các lệnh cộng [add] và trừ [subtract] là:

ADD đích, nguồn

SUB đích, nguồn

Mô tả: ADD: Đích  Đích + Nguồn

SUB : Đích  Đích -Nguồn

trong đó các toán hạng đích, nguồn có thể tìm được theo các địa chỉ khác nhau, nhưng phải chứa dữ liệu có cùng độ dài và không được phép đồng thời là hai ô nhớ và cũng không được là thanh ghi đoạn.

Bảng 4-4 tóm tắt các loại khác nhau của các toán hạng đích và nguồn dùng trong các lệnh cộng và trừ:

Bảng 4-4. các dạng toán hạng trong lệnh ADD/SUB:

Đích [nơi đến] Nguồn [gốc]

Thanh ghi

Thanh ghi

Bộ nhớ

Bộ nhớ

Thanh ghi Thanh ghi

Bộ nhớ

Thanh ghi

Tức thời [hằng số]

Tức thời[hằng số]

Ví dụ 1:

ADD AX, BX ; AX  AX+BX

ADD AL, 74H ; AX  AX+ 74H

SUB CL, AL ; CL  CL - AL

SUB AX, 0405H ; AX  AX - 0405H.

Ví dụ 2: Viết đoạn chương trình ngôn ngữ assembly để cộng 5H với 3H, dùng các thanh ghi AL, BL.

MOV AL, 05H ; AL  05H

MOV BL, 03H ; BL  03H

ADD AL, BL ; AL  05H+03H =08H

MOV 100H, AL ; Di chuyển kết quả từ AL vào vị trí nhớ DS:100H.

MUL/DIV Dạng tổng quát của lệnh nhân [multiply, MUL] và chia [divide, DIV] là:

MUL số nhân nguồn

DIV số chia nguồn

trong đó số nhân nguồn [toán hạng gốc] có thể tìm được theo các chế độ địa chỉ khác nhau. Khi dùng lệnh nhân, số được nhân phải được chuyển vào thanh ghi AX hoặc AL. Còn số nhân thì có thể chuyển vào thanh ghi khác bất kỳ hoặc một địa chỉ nhớ.

Ví dụ 2:

MUL BX ; số nhân nằm trong thanh ghi BX

MUL MEM1 ; số nhân nằm trong địa chỉ nhớ mang nhãn MEM1

Khi hai byte nhân với nhau thì kết quả được gửi lưu vào thanh ghi AX.

Ví dụ 3. Viết đoạn chương trình nhân 5H với 3H, dùng thanh ghi CL.

MOV AL, 05H ; AL  05H [số được nhân]

MOV CL, 03H ; CL  03H [số nhân]

MUL CL ; AL  0FH [kết quả]

MOV MEM1, AL ; chuyển kết quả [0FH]

; từ AL vào vị trí nhớ có nhãn MEM1.

Khi nhân hai lời [16 bit] với nhau thì số được nhân phải chuyển vào thanh ghi AX, còn số nhân có thể ở trong một thanh ghi khác bất kỳ hoặc trong vị trí nhớ 16 bite. kết quả sẽ là con số 32 bit [hoặc hai lời] và được chứa trong các thanh ghi DX và AX. Lời có trọng số lớn sẽ ở trong thanh ghi DX và lời có trọng số nhỏ sẽ ở trong thanh ghi AX.

Ví dụ 4. Viết đoạn chương trình để nhân 3A62H với 2B14H.

MOV AX, 3A62H ; AX  3A62H

MOV CX, 2B14H ; CX  2B14H

MUL CX ; DXAX  tích = 289C63A8H

Các lệnh chia, về cơ bản, cũng giống như các lệnh nhân. Trong phép chia cỡ byte, số chia là một byte có thể ở trong một thanh ghi hoặc một vị trí nhớ. Số bị chia phải là một số không dấu 16 bit chứa trong thanh ghi AX. Kết quả thương số sẽ ở trong thanh ghi AL, còn số dư thì ở trong thanh ghi AH. Đối với phép chia cỡ lời thì số chia 16 bit có thể đặt trong thanh ghi hoặc một vị trí nhớ. Còn số bị chia phải là một số không dấu 32 bit được đặt trong các thanh ghi DX và AX. Thanh ghi DX sẽ giữ lời có trọng số cao, thanh ghi AX sẽ giữ lời có trọng số thấp. Kết quả thương đặt trong thanh ghi AX, còn số dư đặt trong thanh ghi DX.

Ví dụ 5: Viết đoạn chương trình để chia 6H cho 3H, dùng thanh ghi CL. MOV AX, 0006H ; AX  6H

MOV CL, 03H ; CL  3H

DIV CL ; AHAL  00H [số dư], 02H [thương số]

Chú ý: 6H được đưa vào thành 0006H để lấp đầy toàn bộ thanh ghi AX. Như vậy các byte trọng số cao của AX sẽ bị xoá để tránh bị lỗi.

Ví dụ 6: Viết đoạn chương trình để chia 1A034H cho 1002H, dùng thanh ghi BX

MOV AX, 0A034H ; AX  0A034H

MOV DX, 0001H ; DX  0001H

MOV BX, 1002H ; BX  1002H

DIV BX ; DXAX  00H [số dư]1AH [thương số]

INC/DEC Đây là lệnh tăng [increment] và giảm [decrement]. Lệnh tăng sẽ cộng thêm một đơn vị vào toán hạng, còn lệnh giảm sẽ trừ một đơn vị vào toán hạng. Các lệnh này rất cần đối với thao tác đếm. Dạng tổng quát của các lệnh INC và DEC là:

INC đích Mô tả: Đích  Đích +1

DEC đích Mô tả: Đích  Đích -1

Toán hạng đích có thể là một thanh ghi hoặc một vị trí nhớ bất kỳ, có thể là 1 lời 16 bit hoặc 1 byte; có thể tìm được theo các chế độ địa chỉ khác nhau.

Chú ý:

- Trong lệnh tăng, nếu Đích = FFH [hoặc FFFFH] thì Đích + 1 = 00H [hoặc 0000H] mà không ảnh hưởng đến cờ nhớ. Lệnh này cho kết quả tương đương như lệnh ADD Đích, 1 nhưng chạy nhanh hơn.

- Trong lệnh giảm, nếu đích là 00H [hoặc 0000H] thì Đích -1 = FFH [hoặc FFFFH] mà không ảnh hưởng đến cờ nhớ CF. Lệnh này cho kết quả tương đương với lệnh SUB Đích, 1 nhưng chạy nhanh hơn.

NEG- Negative a Operand [lấy bù 2 của một toán hạng hay đảo dấu toán hạng].

Viết lệnh: NEG Đích

Ví dụ:

NEG AH ; AH  0 - [AH]

NEG BYTE PTR[BX] ; lấy bù 2 của ô nhớ do BX chỉ ra trong DS.

II.3. Nhóm lệnh logic [có ảnh hưởng đến cờ].

Các lệnh logic nhằm thực hiện các phép tính Boolean NOT, AND và OR. Lệnh NOT thì đảo tất cả các bit trong toán hạng [byte boặc lời]. Các lệnh AND/OR thực hiện các phép tính AND/OR đối với một đôi bit trong toán hạng nguồn và toán hạng đích. Các lệnh này có thể dùng với các toán hạng cỡ lời hoặc cỡ byte.

NOT Lấy bù của một toán hạng, đảo bit của một toán hạng.

Viết lệnh: NOT Đích. Mô tả: Đích  [Đích]

trong đó toán hạng đích có thể tìm được theo các chế độ địa chỉ khác nhau.

Lệnh này không tác động đến cờ.

Ví dụ 1: Xác định kết quả của đoạn chương trình sau:

MOV BL, 00110011B

NOT BL

MOV MEM1, BL

Nội dung của thanh ghi BL được nạp vào là 00110011B. Sau khi thực hiện phép NOT thì nội dung của thanh ghi BL là 11001100B và giá trị này được đưa vaò vị trí nhớ được chỉ ra bởi nhãn MEM1.

AND/OR: Và/Hoặc hai toán hạng. dạng tổng quát của lệnh AND/OR là:

AND Đích, Nguồn

OR Đích, Nguồn

trong đó toán hạng đích và nguồn có thể tìm được theo các chế độ địa chỉ khác nhau, nhưng phải chứa dữ liệu cùng độ dài và không được phép đồng thời là hai ô nhớ và cũng không được là thanh ghi đoạn.

AND/OR sẽ thực hiện phép tính Boolean đối với các toán hạng nguồn và đích. Phép AND thường dùng để che đi/giữ lại một vài bit nào đó của một toán hạng bằng cách nhân logic toán hạng đó với toán hạng tức thời có các bit 0/1 tại các vị trí cần che/giữ lại tương ứng. Phép OR thường dùng để lập một vài bit nào đó của toán hạng bằng cách cộng lôgic toán hạng đó với toán hạng tức thời có các bit 1 tại các vị trí tương ứng cần thiết lập [toán hạng tức thời trong những trường hợp này còn được gọi là mặt nạ].

Ví dụ 2 :

AND AL, BL ; nội dung thanh ghi BL được giao với nội dung trong

; thanh ghi AL và kết quả được lưu trong thanh ghi

; AL[AX]. Nếu con số trong AL là 00001101B và

; trong BL là 00110011B thì kết quả trong thanh ghi

; AL sau phép AND là: AL 0000001B.

OR AL, BL ; nội dung thanh ghi BL được hợp với nội dung trong

; thanh ghi AL từng bit một và kết quả được lưu trong

;thanh ghi AL[AX]. Nếu con số trong AL là

; 00001101B và trong BL là 00110011B thì kết quả

;trong thanh ghi AL sau phép AND là: AL 0011111B.

Ví dụ 3:

AND BL, 0FH ; che 4 bit cao của BL.

OR BL, 30H ; lập 4 bit b4 và b5 của BL lên 1.

SAL- Shift arithmetically Left [Dịch trái số học]/ SHL- Shift [Logically] Left [Dịch trái logic].

Viết lệnh: SAL Đích, CL

SHL Đích, CL

Mô tả:

Mỗi lần dịch MSB sẽ được đưa qua cờ CF và 0 được đưa vào LSB. Thao tác kiểu này được gọi là dịch logic. CL phải được chứa sẵn số lần dịch mong muốn. Thực chất mỗi lần dịch trái tương đương với một lần làm phép nhân với 2 của số không dấu. Vì vậy ta có thể làm phép nhân số bị nhân không dấu với 2i bằng cách dịch trái số học số bị nhân i lần. Chính vì vậy thao tác này còn được gọi là dịch trái số học.

Sau lệnh SAL/SHL, cờ CF mang giá trị cũ của MSB, vì vậy lệnh này cò dùng để tạo cờ CF từ giá trị của MSB làm điều kiện cho các lệnh nhảy có điều kiện. Còn cờ OF  1 nếu sau khi dịch 1 lần mà bit MSB bị thay đổi so với trước khi dịch, cờ này không được xác định sau nhiều lần dịch.

Lệnh này cập nhật các cờ SF, ZF, PF. Trong đó PF chỉ có ý nghĩa khi toán hạng là 8 bit; cờ AF không xác định.

SAR - Shift Arithmetically Right [Dịch phải số học].

Viết lệnh: SAR Đích, CL

Mô tả:

Sau mỗi lần dịch phải, MSB được giữ nguyên [nếu đây là bit dấu thì dấu luôn không đổi sau các lần dịch. Còn LSB được đưa vào cờ CF, CL phải được chứa sẵn số lần dịch mong muốn. Kiểu dịch này tương đương với một lần chia cho 2của số có dấu. Vì vậy có thể thay phép chia cho 2

ROL - Rotate All Bit to the Left [Quay vòng sang trái].

Viết lệnh: ROL Đích, CL

Mô tả:

Lệnh này dùng để quay toán hạng sang trái, MSB sẽ được đưa qua cờ CF và LSB. CL phải chứa số lần quay mong muốn.

Sau lệnh ROL cờ CF mang giá trị cũ của MSB, vì vậy lệnh này cò dùng để tạo cờ CF từ giá trị của MSB làm điều kiện cho các lệnh nhảy có điều kiện. Còn cờ OF  1 nếu sau khi dịch 1 lần mà bit MSB bị thay đổi so với trước khi dịch, cờ này không được xác định sau nhiều lần dịch. Lệnh này tác động vào các cờ CF, OF.

Ví dụ:

ROL BX, 1 ; quay vòng sang trái thanh ghi BX.

MOV CL, 4 ; đặt số lần quay vào thanh ghi CL.

ROL AL, CL ; quay vòng sang trái thanh ghi AL 4 lần.

ROR - Rotate All Bit to the Right [Quay vòng sang phải].

Viết lệnh: ROR Đích, CL

Mô tả:

Lệnh này dùng để quay toán hạng sang phải, LSB sẽ được đưa qua cờ CF và MSB. CL phải chứa số lần quay mong muốn.

II.4. Nhóm lệnh so sánh.

CMP - Compare Byte or Word [so sánh 2 byte hay 2 từ].

Viết lệnh: CMP Đích, Gốc.

Trong đó toán hạng đích và gốc có thể tìm được theo các chế độ địa chỉ khác nhau, nhưng phải chữa dữ liệu có cùng độ dài và không được phép đồng thời là 2 ô nhớ.

Lệnh này chỉ tạo các cờ, không lưu kết quả so sánh; sau lệnh so sánh, các toán hạng không bị thay đổi. lệnh này thường được dùng để tạo cờ cho các lệnh nhảy có điều kiện.

Các cờ chính theo quan hệ đích và nguồn khi so sánh 2 số không dấu:

CF ZF

Đích = Nguồn 0 1

Đích > Nguồn 0 0

Đích < Nguồn 1 0.

TEST - And Operands to Update Flag [và 2 toán hạng để tạo cờ].

Viết lệnh: TEST Đích, Nguồn

Trong đó toán hạng đích và nguồn có thể tìm được theo các chế độ địa chỉ khác nhau, nhưng phải chứa dữ liệu cùng độ dài và không được phép đồng thời là 2 ô nhớ và cũng không được là thanh ghi đoạn. Sau lệnh này các toán hạng không bị thay đổi và kết quả không được lưu giữ. Các cờ được tạo ra sẽ được dùng làm điều kiện cho các lệnh nhảy có điều kiện. Lệnh này cũng có tác dụng che như một mặt nạ.

Tác động: Xoá: CF, OF

Cập nhật: PF, SF, ZF [PF chỉ liên quan đến 8 bit thấp]

Không xác định: AF.

Ví dụ:

TEST AH, AL ; Và AH với AL để tạo cờ.

TEST AH, 01H ; Bit 0 của AH = 0?

TEST BP, [BX][DI] ; Và BP với ô nhớ DS:BX+DI.

II.5 Các lệnh điều khiển chương trình.

- Lệnh nhảy không điều kiện: Lệnh này khiến bộ vi xử lý bắt đầu thực hiện một lệnh mới tại địa chỉ được mô tả trong lệnh.

Viết lệnh: JMP Nhãn

Lệnh mới bắt đầu tại địa chỉ ứng với nhãn. Chương trình dịch sẽ căn cứ vào vị trí nhãn để xác định giá trị dịch chuyển.

- Lệnh nhảy có điều kiện: Lệnh này biểu diễn thao tác: nhảy [có điều kiện] tới nhãn, tức là chỉ thực hiện nhảy tới nhãn nếu điều kiện chỉ ra đúng. Nhãn phải nằm cách xa [dịch đi một khoảng] -128.. +127 byte so với lệnh tiếp theo sau lệnh nhảy có điều kiện. Chương trình dịch sẽ căn cứ vào vị trí của nhãn để xác định giá trị dịch chuyển.

Các lệnh này không tác động đến cờ.

Người ta phân biệt các kiểu nhảy có điều kiện:

+ Nhảy theo kiểu không dấu:

JA/JNBE - Jump if Above/ Jump if Not Below or Equal.

Viết lệnh: JA Nhãn

JNBE Nhãn

JAE/JNB- Jump if Above or Equal/ Jump if Not Below.

Viết lệnh: JAE Nhãn

JNB Nhãn

JB/JNAE- Jump if Below/ Jump if Not Above or Equal.

Viết lệnh: JB Nhãn

JNAE Nhãn.

Ví dụ 1:

CMP AL, 10H ; so sánh AL với 10H.

JA MEM1 ; nhảy đến nhãn MEM1 nếu AL cao hơn 10H.

JB MEM2 ;nhảy đến nhãn MEM2 nếu AL thấp hơn 10H.

+ Nhảy theo kiểu có dấu:

JG/JNLE- Jump if Greater than/ Jump if Not Less than or Equal.

Viết lệnh: JG Nhãn

JNLE Nhãn.

JGE/JNL- Jump if Greater than or Equal/ Jump if Not Less than.

Viết lệnh: JGE Nhãn

JNL Nhãn.

JL/JNGE- Jump if Less than/ Jump if Not Greater than or Equal.

JLE/JNG- Jump if Less than or Equal/ Jump if Not Greater than.

+ Nhảy theo kiểu đơn.

JE/JZ- Jump if Equal/ Jump if Zero.

JNE/JNZ- Jump if Not Equal/ Jump if Not Zero.

JC- Jump if Carry

JNC- Jump if Not Carry

JO- Jump if Overflow

JNO- Jump if Not Overflow

JS- Jump if Sign

JNS- Jump if Not Sign

JP/JPE- Jump if Parity/ Jump if Parity Even

JNP/JPO- Jump if Not Parity/ Jump if Parity Odd

- Lệnh lặp: Lệnh này dùng để lặp lại đoạn chương trình [bao gồm các lệnh nằm trong khoảng tử nhãn đến hết lệnh LOOP Nhãn cho đến khi số lần lặp CX=0. Điều này có nghĩa là trước khi vào vòng lặp, ta phải đưa số lần lặp mong muốn vào thanh ghi CX và sau mỗi lần thực hiện lệnh LOOP Nhãn thì CX tự động giảm đi 1.

Nhãn phải nằm cách xa [dịch một khoảng] -128 byte so với lệnh tiếp theo sau lệnh LOOP.

Lệnh này không tác động đến cờ.

Viết lệnh: LOOP Nhãn

Ví dụ:

XOR AL, Al ; xoá AL

MOV CX, 16 ; số lần lặp đưa vào CX

Lap: INC AL ; tăng AL lên 1

LOOP Lap ; lặp lại 16 lần, AL =16.

- Lệnh JCXZ- Jump if CX is Zero [nhảy nếu CX = 0].

Viết lệnh: JCXZ Nhãn

Đây là lệnh nhảy có điều kiện tới nhãn nếu nội dung thanh đếm bằng 0 và không có liên hệ gì với cò ZF. Nhãn phải nằm cách xa [dịch đi một khoảng] -128.. +127 byte so với lệnh tiếp theo sau lệnh JCXZ. Chương trình dịch sẽ căn cứ vào vị trí nhãn để xác định giá trị dịch chuyển.

- Lệnh gọi chương trình con CALL: Lệnh này dùng để chuyển hoạt động của bộ vi xử lý từ chương trình chính [CTC] sang chương trình con [ctc]. Nếu ctc ở cùng một đoạn mã với CTC thì ta có gọi gần. Nếu CTC và ctc nằm trong hai đoạn mã khác nhau thì ta có gọi xa. Gọi gần và gọi xa khác nhau về cách tạo địa chỉ trở về. Địa chỉ trở về là địa chỉ tiếp theo ngay sau lệnh CALL. Khi gọi gần thì chỉ cần cất IP của địa chỉ trở về, khi gọi xa thì phải cất cả CS và IP của địa chỉ trở về. Địa chỉ trở về được tự động cất vào ngăn xếp khi bắt đầu thựuc hiện lệnh gọi và được tự động lấy ra khi gặp lệnh trở về RET.

-RET - Return from Procedure to Calling Program [Trở về CTC từ ctc].

Viết lệnh: RET

Khi gặp lệnh trở về RET, vi xử lý kết thúc ctc lấy lại địa chỉ trở về, bao gồm địa chỉ IP [trường hợp gọi gần] hoặc IP và CS [trong trường hợp gọi xa] của lệnh tiếp theo sau lệnh CALL, được đặt trong ngăn xếp.

- INT - Interrupt Program Excution [Ngắt, gián đoạn chương trình đang chạy].

Viết lệnh: INT N, N = 0.. FFH

Mô tả: Các thao tác của bộ vi xử lý khi chạy lệnh INT :

1. SP  SP - 2. {SP}  FR

2. IF  0 [cấm các ngắt khác tác động], TF  0 [chạy suốt].

3. SP  SP - 2, {SP}  CS.

4. SP  SP - 2, {SP}  IP.

5. {N x 4}  IP, {5N x 4 + 2}  CS.

Mỗi lệnh ngắt ứng với một chương trình phục vụ ngắt khác nhau có địa chỉ lấy từ bảng véc tơ ngắt. Bảng này gômg 256 vec tơ, chứa địa chỉ của các chương trình phục vụ ngắt tương ứng và chiếm 1 Kb RAM có địa chỉ thấp nhất.

Ví dụ như các chương trình phục vụ ngắt của BIOS, của DOS như IO.SYS, MSDOS.SYS.

Ví dụ:

INT 21H

III. Các chế độ địa chỉ

Những phương pháp định địa chỉ hay còn gọi là chế độ địa chỉ [addressing mod] được dùng để vi xử lý tìm ra [định vị, addressing] các toán hạng cần thiết cho một lệnh nào đó. Một bộ vi xử lý có thể có nhiều chế độ địa chỉ, các chế độ địa chỉ này được xác định ngay từ khi chế tạo bộ vi xử lý và sau này không thể thay đổi được. Họ vi xử lý Intel có bảy chế độ địa chỉ như sau:

1. Chế độ địa chỉ thanh ghi

2. Chế độ địa chỉ tức thì

3. Chế độ địa chỉ trực tiếp

4. Chế độ địa chỉ gián tiếp thanh ghi

5. Chế độ địa chỉ tương đối cơ sở

6. Chế độ địa chỉ tương đối chỉ số

7. Chế độ địa chỉ tương đối chỉ số cơ sở

III.1. Chế độ địa chỉ thanh ghi [register addressing].

Trong chế độ địa chỉ này người ta dùng các thanh ghi bên trong CPU như là các toán hạng để chứa dữ liệu cần thao tác. Vì vậy khi thực hiện lệnh có thể đạt tốc độ truy nhập cao hơn so với các lệnh có truy nhập đến bộ nhớ.

Ví dụ:

MOV AX, BX ; chuyển nội dung BX vào AX.

ADD DS, DL ; cộng nội dung AL và DL , kết quả giữ trong AL.

III.2. Chế độ địa chỉ tức thì [immediate addressing]

Trong chế độ địa chỉ này toán hạng đích là một thanh ghi hay một ô nhớ, còn toán hạng nguồn là một hằng số và ta có thể tìm thấy toán hạng này ở ngay sau mã lệnh [chính vì vậy chế độ địa chỉ này gọi là chế độ địa chỉ tức thì]. Ta có thể dùng chế độ này để nạp dữ liệu cần thao tác vào bất kỳ thanh ghi nào [trừ các thanh ghi đoạn và các thanh ghi cờ] hoặc vào bất kỳ ô nhớ nào trong đoạn dữ liệu DS.

Ví dụ:

MOV AX, 4EH ; chuyển giá trị 4EH vào thanh ghi AX.

MOV AX, 0FFOH ; chuyển 0FF0H vào thanh ghi AX

MOV DS, AX ; để đưa vào DS.

MOV [BX], 4EH ; chuyển 4EH vào địa chỉ ô nhớ DS:BX

III.3. Chế độ địa chỉ trực tiếp [direct addresssing mode]

Trong chế độ địa chỉ này một toán hạng chứa địa chỉ lệch của ô nhớ dùng để chứa dữ liệu, còn toán hạng kia chỉ có thể là một thanh ghi mà không thể là một vị trí nhớ.

Nếu so sánh với chế độ địa chỉ tức thì ta thấy ở đây ngay sau mã lệnh không phải là một toán hạng mà là một địa chỉ lệch của toán hạng. Xét về phương diện địa chỉ thì đó là địa chỉ trực tiếp.

Ví dụ:

MOV AL, [1234H] ; chuyển nội dung ô nhớ DS:1234H vào AL.

MOV [4321H], CX ; chuyển nội dung CX vào 2 vị trí nhớ

; liên tiếp là DS:4321 và DS:4322.

III.4. Chế độ địa chỉ gián tiếp qua thanh ghi [register indirect addressing].

Trong chế độ địa chỉ này một toán hạng là một thanh ghi được sử dụng để chứa địa chỉ lệch của ô nhớ chứa dữ liệu, còn toán hạng kia chỉ có thể là một thanh ghi mà không được là ô nhớ.

Ví dụ:

MOV AL, [BX] ; chuyển nội dung tại ô nhớ DS:BX vào AL.

MOV [SI], CL ; chuyển nội dung CL vào ô nhớ DS:SI.

III.5. Chế độ địa chỉ tương đối cơ sở [based relative addresing].

Trong chế độ này các thanh ghi cơ sở như BX và BP và các hằng số biểu diễn các giá trị dịch chuyển [displacement values] được dùng để tính địa chỉ hiệu dụng của toán hạng trong các vùng nhớ DS và SS. Sự có mặt của các giá trị diạch chuyển xác định tính tương đối [so với cơ sở] của địa chỉ.

Ví dụ:

MOV CL, [BX] + 10 ; chuyển nội dung 2 ô nhớ liên tiếp có địa

; chỉ DS:[BX+10] và DS:[BX+11] vào CX.

MOV CX, [BX +10] ; tương tự như lệnh trên.

MOV AL, [BP] + 10 ; chuyển nội dung ô nhớ SS:[BP+10] vào AL

III. 6. Chế độ địa chỉ tương đối chỉ số [indexed relative addressing].

Trong chế độ địa chỉ này các thanh ghi chỉ số như SI và DI và các hằng số biểu diễn các giá trị dịch chuyển [displacement values] được dùng để tính địa chỉ của toán hạng trong vùng nhớ DS.

Ví dụ:

MOV AL, [SI]+10 ; chuyển nội dung ô nhớ DS:[SI+10] vào AL.

MOV AL, [SI+10] ; tương tự như trên.

III.7. Chế độ địa chỉ tương đối chỉ số cơ sở [based indexed relative addressing].

Kết hợp hai chế độ địa chỉ chỉ số và cơ sở ta có chế độ địa chỉ chỉ số cơ sở. Trong chế độ địa chỉ này ta dùng cả thanh ghi cơ sở và thanh ghi chỉ số để tính địa chỉ của toán hạng. Nếu ta dùng thêm cả thành phần biểu diễn sự dịch chuyển của địa chỉ thì ta có chế độ địa chỉ phức hợp cho chế độ địa chỉ hoá các mảng hai chiều.

Ví dụ:

MOV AL, [BP][SI]+10 ; chuyển nội dung DS:[BX+SI+10] vào AL.

MOV AL, [BP+SI+10] ; tương tự như trên.

Khi dùng thanh ghi chỉ số , thanh ghi cơ sở và thanh ghi con trỏ thì những cặp địa chỉ đoạn và địa chỉ lệch sau sẽ được định nghĩa trước:

CS:IP, DS:SI, DS:DI, DS:BX, ES:DI, SS:SP, SS:BP.

Muốn loại bỏ giá trị ngầm định cho BX trong thanh ghi đoạn DS và dùng giá trị trong thanh ghi đoạn ES ta cần viết:

MOV AL, ES:[BX] ; chuyển nội dung ES:BX vào AL.

Video liên quan

Chủ Đề