همراهان عزیز وب سایت آموزشی پی وی لرن وقتتون بخیر و شادی، با آموزش زبان برنامه نویسی اسمبلی (Assembly) در خدمتتون خواهیم بود. دستورالعملهای محاسباتی در زبان اسمبلی (Assembly) را با بررسی دستورالعمل MUL / IMUL و دستورالعمل های ADD و SUB و غیره آغاز می کنیم. با ما همراه باشید.
دستورالعمل INC يک واحد به عملوند خود اضافه خواهد کرد. این بر روی یک عملگر واحد کار می کند که می تواند در یک رجیستر یا حافظه باشد.
دستورالعمل INC دارای سینتکس زیر است.
1 | INC destination |
مقصد عملوند می تواند یک عملوند ۸ بیتی ، ۱۶ بیتی یا ۳۲ بیتی باشد.
مثال
1 2 3 | INC EBX ; Increments 32-bit register INC DL ; Increments 8-bit register INC [count] ; Increments the count variable |
دستورالعمل DEC يک واحد از عملوند خود کم خواهد کرد. این بر روی یک عملگر واحد کار می کند که می تواند در یک رجیستر یا حافظه باشد.
دستورالعمل DEC دارای سینتکس زیر است.
1 | DEC destination |
مقصد عملوند می تواند یک عملوند ۸ بیتی ، ۱۶ بیتی یا ۳۲ بیتی باشد.
مثال
1 2 3 4 5 6 7 8 9 10 11 12 13 | segment .data count dw 0 value db 15 segment .text inc [count] dec [value] mov ebx, count inc word [ebx] mov esi, value dec byte [esi] |
دستورالعمل های ADD و SUB برای اضافه یا تفریق ساده از داده های باینری در اندازه های بایت ، word و doubleword ، یعنی برای اضافه کردن یا تفریق عملوندهای ۸ بیتی ، ۱۶ بیتی یا ۳۲ بیتی به ترتیب استفاده می شود.
سینتکس
دستورالعمل های ADD و SUB دارای سینتکس زیر هستند.
1 | ADD/SUB destination, source |
دستورالعمل ADD / SUB می تواند به شکل های زير استفاده شود:
اما ، مانند سایر دستورالعمل ها ، عملکرد memory-to-memory با استفاده از دستورالعمل های ADD / SUB امکان پذیر نیست. یک عملیات ADD یا SUB سرریز (overflow) و یا carry flag ها را تنظیم می کند.
در مثال زیر دو رقم از کاربر خواسته می شود ، ارقام را در دجیستر EAX و EBX ذخیره کنید ، مقادیر را اضافه کنید ، نتیجه را در مکان حافظه “res” ذخیره کنید و در آخر نتیجه را نمایش دهید.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 | SYS_EXIT equ 1 SYS_READ equ 3 SYS_WRITE equ 4 STDIN equ 0 STDOUT equ 1 segment .data msg1 db "Enter a digit ", 0xA,0xD len1 equ $- msg1 msg2 db "Please enter a second digit", 0xA,0xD len2 equ $- msg2 msg3 db "The sum is: " len3 equ $- msg3 segment .bss num1 resb 2 num2 resb 2 res resb 1 section .text global _start ;must be declared for using gcc _start: ;tell linker entry point mov eax, SYS_WRITE mov ebx, STDOUT mov ecx, msg1 mov edx, len1 int 0x80 mov eax, SYS_READ mov ebx, STDIN mov ecx, num1 mov edx, 2 int 0x80 mov eax, SYS_WRITE mov ebx, STDOUT mov ecx, msg2 mov edx, len2 int 0x80 mov eax, SYS_READ mov ebx, STDIN mov ecx, num2 mov edx, 2 int 0x80 mov eax, SYS_WRITE mov ebx, STDOUT mov ecx, msg3 mov edx, len3 int 0x80 ; moving the first number to eax register and second number to ebx ; and subtracting ascii '0' to convert it into a decimal number mov eax, [num1] sub eax, '0' mov ebx, [num2] sub ebx, '0' ; add eax and ebx add eax, ebx ; add '0' to to convert the sum from decimal to ASCII add eax, '0' ; storing the sum in memory location res mov [res], eax ; print the sum mov eax, SYS_WRITE mov ebx, STDOUT mov ecx, res mov edx, 1 int 0x80 exit: mov eax, SYS_EXIT xor ebx, ebx int 0x80 |
هنگامی که کد فوق کامپایل و اجرا شد ، نتیجه زیر را ایجاد می کند.
1 2 3 4 5 6 | Enter a digit: 3 Please enter a second digit: 4 The sum is: 7 |
برنامه با متغیرهای hardcoded شده :
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 | section .text global _start ;must be declared for using gcc _start: ;tell linker entry point mov eax,'3' sub eax, '0' mov ebx, '4' sub ebx, '0' add eax, ebx add eax, '0' mov [sum], eax mov ecx,msg mov edx, len mov ebx,1 ;file descriptor (stdout) mov eax,4 ;system call number (sys_write) int 0x80 ;call kernel mov ecx,sum mov edx, 1 mov ebx,1 ;file descriptor (stdout) mov eax,4 ;system call number (sys_write) int 0x80 ;call kernel mov eax,1 ;system call number (sys_exit) int 0x80 ;call kernel section .data msg db "The sum is:", 0xA,0xD len equ $ - msg segment .bss sum resb 1 |
هنگامی که کد فوق کامپایل و اجرا شد ، نتیجه زیر را ایجاد می کند.
1 2 | The sum is: 7 |
برای ضرب داده های باینری دو دستورالعمل وجود دارد. دستورالعمل (MUL (Multiply داده های بدون علامت را، و (IMUL (Integer Multiply داده های علامت دار را مدیریت می کند. هر دو دستورالعمل روی Carry و Overflow flag تأثیر می گذارند.
سینتکس دستورالعمل MUL / IMUL به شرح زیر است.
1 | MUL/IMUL multiplier |
دستور ضرب بسته به اندازه تک عملوند خود به چند شکل ممکن است عمل کند. بخش زیر دستورالعمل MUL را توضیح می دهد.
ردیف | سناریوها |
---|---|
۱ | در صورتی که عملوند یک بایتی باشد، عملوند را در AL ضرب کرده نتيجه را در AX ذخيره می کند. ۸ بیت نتیجه با مرتبه بالا در AH ذخیره می شود و ۸ بیت با مرتبه پایین در AL ذخیره می شود. |
۲ | در صورتی که عملوند دو بايتی (یک کلمه) باشد، عملوند را در AX ضرب کرده نتيجه را در ثبات DX:AX قرار می دهد. به عبارتی نتیجه حاصل شده یک doubleword است که به دو ثبات نیاز دارد. قسمت مرتبه بالا (سمت چپ) در DX ذخیره می شود و قسمت مرتبه پایین (سمت راست) در AX ذخیره می شود.
The multiplicand should be in the AX register, and the multiplier is a word in memory or another register. For example, for an instruction like MUL DX, you must store the multiplier in DX and the multiplicand in AX. The resultant product is a doubleword, which will need two registers. The high-order (leftmost) portion gets stored in DX and the lower-order (rightmost) portion gets stored in AX. |
۳ | وقتی عملوند دو مقدار doubleword باشد، عملوند را در EAX ضرب کرده و نتیجه تولید شده در ثبات EDX:EAX ذخیره می شود ، یعنی ۳۲ بیت مرتبه بالا در رجیستری EDX ذخیره می شود و ۳۲ بیت مرتبه پایین در ثبات EAX ذخیره می شود. |
1 2 3 4 5 6 7 | MOV AL, 10 MOV DL, 25 MUL DL ... MOV DL, 0FFH ; DL= -1 MOV AL, 0BEH ; AL = -66 IMUL DL |
مبحث دستورالعملهای محاسباتی در زبان اسمبلی (Assembly) را با مثالی ادامه می دهیم.
مثال زیر ۳ را با ۲ ضرب می کند و نتیجه را نمایش می دهد.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 | section .text global _start ;must be declared for using gcc _start: ;tell linker entry point mov al,'3' sub al, '0' mov bl, '2' sub bl, '0' mul bl add al, '0' mov [res], al mov ecx,msg mov edx, len mov ebx,1 ;file descriptor (stdout) mov eax,4 ;system call number (sys_write) int 0x80 ;call kernel mov ecx,res mov edx, 1 mov ebx,1 ;file descriptor (stdout) mov eax,4 ;system call number (sys_write) int 0x80 ;call kernel mov eax,1 ;system call number (sys_exit) int 0x80 ;call kernel section .data msg db "The result is:", 0xA,0xD len equ $- msg segment .bss res resb 1 |
هنگامی که کد فوق کامپایل و اجرا شد ، نتیجه زیر را ایجاد می کند.
1 2 | The result is: 6 |
دستورالعملهای محاسباتی در زبان اسمبلی (Assembly) را با دستورالعمل MUL / IMUL مورد بررسی قرار دادیم. در بخش بعدی نیز مبحث دستورالعمل های محاسباتی را با مبحث دستورالعمل DIV / IDIV ادامه خواهیم داد. با ادامه ی آموزش ها از وب سایت آموزشی پی وی لرن همراه باشید.