アセンブリ-論理命令
プロセッサ命令セットは、プログラムの必要性に応じてビットをテスト、セット、およびクリアする命令AND、OR、XOR、TEST、およびNOTブール論理を提供します。
これらの命令のフォーマット-
シニア番号 | 命令 | フォーマット |
---|---|---|
1 | そして | ANDオペランド1、オペランド2 |
2 | または | ORオペランド1、オペランド2 |
3 | XOR | XORオペランド1、オペランド2 |
4 | テスト | TESTオペランド1、オペランド2 |
5 | ない | NOTオペランド1 |
すべての場合の最初のオペランドは、レジスタまたはメモリのいずれかにあります。2番目のオペランドは、レジスタ/メモリまたは即値(定数)のいずれかになります。ただし、メモリ間の操作はできません。これらの命令は、オペランドのビットを比較または照合し、CF、OF、PF、SF、およびZFフラグを設定します。
AND命令
AND命令は、ビット単位のAND演算を実行して論理式をサポートするために使用されます。ビットごとのAND演算は、両方のオペランドの一致するビットが1の場合は1を返し、それ以外の場合は0を返します。たとえば-
Operand1: 0101
Operand2: 0011
----------------------------
After AND -> Operand1: 0001
AND演算は、1つ以上のビットをクリアするために使用できます。たとえば、BLレジスタに0011 1010が含まれているとします。上位ビットをゼロにクリアする必要がある場合は、0FHとAND演算します。
AND BL, 0FH ; This sets BL to 0000 1010
別の例を見てみましょう。与えられた数が奇数か偶数かをチェックしたい場合、簡単なテストはその数の最下位ビットをチェックすることです。これが1の場合、数値は奇数です。それ以外の場合、数値は偶数です。
番号がALレジスタにあると仮定すると、次のように書くことができます。
AND AL, 01H ; ANDing with 0000 0001
JZ EVEN_NUMBER
次のプログラムはこれを示しています-
例
section .text
global _start ;must be declared for using gcc
_start: ;tell linker entry point
mov ax, 8h ;getting 8 in the ax
and ax, 1 ;and ax with 1
jz evnn
mov eax, 4 ;system call number (sys_write)
mov ebx, 1 ;file descriptor (stdout)
mov ecx, odd_msg ;message to write
mov edx, len2 ;length of message
int 0x80 ;call kernel
jmp outprog
evnn:
mov ah, 09h
mov eax, 4 ;system call number (sys_write)
mov ebx, 1 ;file descriptor (stdout)
mov ecx, even_msg ;message to write
mov edx, len1 ;length of message
int 0x80 ;call kernel
outprog:
mov eax,1 ;system call number (sys_exit)
int 0x80 ;call kernel
section .data
even_msg db 'Even Number!' ;message showing even number
len1 equ $ - even_msg
odd_msg db 'Odd Number!' ;message showing odd number
len2 equ $ - odd_msg
上記のコードをコンパイルして実行すると、次の結果が得られます。
Even Number!
斧レジスタの値を-のように奇数桁で変更します
mov ax, 9h ; getting 9 in the ax
プログラムは次のように表示します。
Odd Number!
同様に、レジスタ全体をクリアするには、00HとANDすることができます。
OR命令
OR命令は、ビット単位のOR演算を実行して論理式をサポートするために使用されます。ビット単位のOR演算子は、いずれかまたは両方のオペランドの一致するビットが1の場合、1を返します。両方のビットがゼロの場合、0を返します。
例えば、
Operand1: 0101
Operand2: 0011
----------------------------
After OR -> Operand1: 0111
OR演算は、1つ以上のビットを設定するために使用できます。たとえば、ALレジスタに0011 1010が含まれていると仮定すると、下位4ビットを設定する必要があります。値0000 1111、つまりFHとORすることができます。
OR BL, 0FH ; This sets BL to 0011 1111
例
次の例は、OR命令を示しています。値5と3をそれぞれALレジスタとBLレジスタに格納してから、命令、
OR AL, BL
ALレジスタに7を格納する必要があります-
section .text
global _start ;must be declared for using gcc
_start: ;tell linker entry point
mov al, 5 ;getting 5 in the al
mov bl, 3 ;getting 3 in the bl
or al, bl ;or al and bl registers, result should be 7
add al, byte '0' ;converting decimal to ascii
mov [result], al
mov eax, 4
mov ebx, 1
mov ecx, result
mov edx, 1
int 0x80
outprog:
mov eax,1 ;system call number (sys_exit)
int 0x80 ;call kernel
section .bss
result resb 1
上記のコードをコンパイルして実行すると、次の結果が得られます。
7
XOR命令
XOR命令は、ビット単位のXOR演算を実装します。XOR演算は、オペランドのビットが異なる場合にのみ、結果のビットを1に設定します。オペランドのビットが同じ(両方0または両方1)の場合、結果のビットは0にクリアされます。
例えば、
Operand1: 0101
Operand2: 0011
----------------------------
After XOR -> Operand1: 0110
XORing それ自体を持つオペランドは、オペランドをに変更します 0。これは、レジスタをクリアするために使用されます。
XOR EAX, EAX
TEST命令
TEST命令はAND演算と同じように機能しますが、AND命令とは異なり、第1オペランドは変更されません。したがって、レジスタ内の数値が偶数か奇数かを確認する必要がある場合は、元の数値を変更せずにTEST命令を使用してこれを行うこともできます。
TEST AL, 01H
JZ EVEN_NUMBER
NOT命令
NOT命令は、ビット単位のNOT演算を実装します。NOT演算は、オペランドのビットを反転します。オペランドは、レジスタまたはメモリのいずれかにあります。
例えば、
Operand1: 0101 0011
After NOT -> Operand1: 1010 1100