-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
0 parents
commit 25ab034
Showing
6 changed files
with
686 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
This is free and unencumbered software released into the public domain. | ||
|
||
Anyone is free to copy, modify, publish, use, compile, sell, or | ||
distribute this software, either in source code form or as a compiled | ||
binary, for any purpose, commercial or non-commercial, and by any | ||
means. | ||
|
||
In jurisdictions that recognize copyright laws, the author or authors | ||
of this software dedicate any and all copyright interest in the | ||
software to the public domain. We make this dedication for the benefit | ||
of the public at large and to the detriment of our heirs and | ||
successors. We intend this dedication to be an overt act of | ||
relinquishment in perpetuity of all present and future rights to this | ||
software under copyright law. | ||
|
||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, | ||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF | ||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. | ||
IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR | ||
OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, | ||
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR | ||
OTHER DEALINGS IN THE SOFTWARE. | ||
|
||
For more information, please refer to <https://unlicense.org> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
# asm8086 IO and Ariphmetic example | ||
[![License](https://img.shields.io/badge/LICENSE-The%20Unlicense-green?style=flat-square)](/LICENSE) [![Version](https://img.shields.io/badge/VERSION-STABLE-green?style=flat-square)](https://github.com/averov90/asm8086-io-ariphmetic/releases) | ||
### :small_orange_diamond: [Russian version](/README.md) | ||
|
||
This repository contains 3 small running programs that contain some I/O and arithmetic functions. To get an example (to be able to demonstrate), each program has a head function. Below, the list of examples will be discussed in more detail. | ||
|
||
To run the examples, you need: a *DOS* environment, a *TASM (Turbo Assembler)* compiler for *Intel 8086*. As a *DOS* environment, you can take *DOSBox* (or *DOSBox Staging*, but in the *DOSBox*, compiled programs seem to work better). | ||
|
||
Before starting each function, it is specified which registers are required for this function to work (i.e., those registers whose value must be stored before calling the function in case the values stored in them are needed later). These registers also include function arguments. The description of these arguments is given inside the function (at the beginning). Many aspects of program execution are explained in the comments in the code. | ||
|
||
## prog_1.asm | ||
**func_uint16IN** - function for entering an unsigned 16-bit number. The number itself is returned after entering via the *AX* register. | ||
|
||
**func_uint32OUT** - function for outputting an unsigned 32-bit number. The number for output is supplied via 2 registers (*AX* - lower word, *DX* - upper word). In operation, this function uses a stack (requires 10 words, i.e. 20 bytes). | ||
|
||
**func_mul32x16** - function for multiplying a 32-bit number by a 16-bit number. The numbers for are fed through 3 registers (*AX* - the lower word of 1 number, *DX* - the upper word of 1 number, *BX* - the multiplier). The result is via *AX* and *DX*. | ||
|
||
**func_div32x16** - function for dividing a 32-bit number by a 16-bit number. Numbers for output are fed through 2 registers (*AX* - the lower word of 1 number, *DX* - the upper word of 1 number, *BX* - the multiplier) and the variable *func_div32x16_divider*. The result is in terms of *AX* and *DX* (integer part), *BX* - remainder. | ||
|
||
The main function of this example uses the above functions to calculate the number of permutations when *m* and *n* are passed to the program. | ||
|
||
## prog_2.asm | ||
**func_int16IN** - function for entering a signed 16-bit number. The number itself is returned after entering via the *AX* register. | ||
|
||
**func_uint16IN** - function for entering an unsigned 16-bit number. The number itself is returned after entering via the *AX* register. | ||
|
||
**func_uint16OUT** - function for outputting an unsigned 16-bit number. The number for output is supplied through 2 registers (*AX* - the lower word). In operation, this function uses a stack (requires 10 words, i.e. 20 bytes). | ||
|
||
The main function of this example uses the above functions to count the number of numbers greater than the specified threshold. Allows you to enter both the threshold and the number of numbers to enter. | ||
|
||
## prog_3.asm | ||
**func_placments32x16x16** - function for calculating the number of permutations for *m* and *n* passed to the program. Arguments to the function are passed through the stack. | ||
|
||
**func_uint16IN** - function for entering an unsigned 16-bit number. The number itself is returned after entering via the *AX* register. | ||
|
||
**func_uint32OUT** - function for outputting an unsigned 32-bit number. The number for output is supplied via 2 registers (*AX* - lower word, *DX* - upper word). In operation, this function uses a stack (requires 10 words, i.e. 20 bytes). | ||
|
||
**func_mul32x16** - function for multiplying a 32-bit number by a 16-bit number. The numbers for are fed through 3 registers (*AX* - the lower word of 1 number, *DX* - the upper word of 1 number, *BX* - the multiplier). The result is via *AX* and *DX*. | ||
|
||
**func_div32x16** - function for dividing a 32-bit number by a 16-bit number. Numbers for output are fed through 2 registers (*AX* - the lower word of 1 number, *DX* - the upper word of 1 number, *BX* - the multiplier) and the variable *func_div32x16_divider*. The result is in terms of *AX* and *DX* (integer part), *BX* - remainder. | ||
|
||
The main function of this example uses the above functions to calculate the number of permutations when *m* and *n* are passed to the program. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
# asm8086 IO and Ariphmetic example | ||
[![License](https://img.shields.io/badge/LICENSE-The%20Unlicense-green?style=flat-square)](/LICENSE) [![Version](https://img.shields.io/badge/VERSION-STABLE-green?style=flat-square)](https://github.com/averov90/asm8086-io-ariphmetic/releases) | ||
### :small_orange_diamond: [English version](/README-eng.md) | ||
|
||
В данном репозитории представлены 3 небольшие работающие программы, которые содержат некоторые функции ввода/вывода и арифметики. Для получения примера (чтобы была возможность демонстрации), в каждой программе есть головная функция. Ниже состав примеров будет рассмотрен подробнее. | ||
|
||
Для запуска примеров необходимо: окружение *DOS*, компилятор *TASM (Turbo Assembler)* для *Intel8086*. В качестве окружения *DOS* можно взять *DOSBox* (либо *DOSBox Staging*, но в старом *DOSBox* скомпилированные программы работают, кажется, лучше). | ||
|
||
Перед началом каждой функцией указано, какие регистры требуются этой функции для работы (т.е. те регистры, значение которых нужно сохранить перед вызовом функции в случае, если хранимые в них значения будут нужны позже). В число этих регистров входят и аргументы функции. Описание этих аргументов даётся внутри функции (в начале). Многие моменты выполнения программ пояснены в комментариях в коде. | ||
|
||
## prog_1.asm | ||
**func_uint16IN** - функция ввода беззнакового 16-битного числа. Само число после ввода возвращается через регистр *AX*. | ||
|
||
**func_uint32OUT** - функция вывода беззнакового 32-битного числа. Число для вывода подаётся через 2 регистра (*AX* - нижнее слово, *DX* - верхнее слово). В работе данная функция использует стек (требует 10 слов т.е. 20 байт). | ||
|
||
**func_mul32x16** - Функция умножения 32-битного числа на 16-битное. Числа для подаются через 3 регистра (*AX* - нижнее слово 1 числа, *DX* - верхнее слово 1 числа, *BX* - множитель). Результат - через *AX* и *DX*. | ||
|
||
**func_div32x16** - функция деления 32-битного числа на 16-битное. Числа для вывода подаются через 2 регистра (*AX* - нижнее слово 1 числа, *DX* - верхнее слово 1 числа, *BX* - множитель) и переменную *func_div32x16_divider*. Результат - через *AX* и *DX* (целая часть), *BX* - остаток. | ||
|
||
Головная функция данного примера с помощью вышеприведённых функций выполняет вычисление количества расстановок при переданных в программу *m* и *n*. | ||
|
||
## prog_2.asm | ||
**func_int16IN** - функция ввода знакового 16-битного числа. Само число после ввода возвращается через регистр *AX*. | ||
|
||
**func_uint16IN** - функция ввода беззнакового 16-битного числа. Само число после ввода возвращается через регистр *AX*. | ||
|
||
**func_uint16OUT** - функция вывода беззнакового 16-битного числа. Число для вывода подаётся через 2 регистра (*AX* - нижнее слово). В работе данная функция использует стек (требует 10 слов т.е. 20 байт). | ||
|
||
Головная функция данного примера с помощью вышеприведённых функций выполняет подсчёт количества чисел, больших заданного порога. Позволяет ввести как порог, так и количество чисел для ввода. | ||
|
||
## prog_3.asm | ||
**func_placments32x16x16** - функция вычисления количества расстановок при переданных в программу *m* и *n*. Аргументы в функцию передаются через стек. | ||
|
||
**func_uint16IN** - функция ввода беззнакового 16-битного числа. Само число после ввода возвращается через регистр *AX*. | ||
|
||
**func_uint32OUT** - функция вывода беззнакового 32-битного числа. Число для вывода подаётся через 2 регистра (*AX* - нижнее слово, *DX* - верхнее слово). В работе данная функция использует стек (требует 10 слов т.е. 20 байт). | ||
|
||
**func_mul32x16** - Функция умножения 32-битного числа на 16-битное. Числа для подаются через 3 регистра (*AX* - нижнее слово 1 числа, *DX* - верхнее слово 1 числа, *BX* - множитель). Результат - через *AX* и *DX*. | ||
|
||
**func_div32x16** - функция деления 32-битного числа на 16-битное. Числа для вывода подаются через 2 регистра (*AX* - нижнее слово 1 числа, *DX* - верхнее слово 1 числа, *BX* - множитель) и переменную *func_div32x16_divider*. Результат - через *AX* и *DX* (целая часть), *BX* - остаток. | ||
|
||
Головная функция данного примера с помощью вышеприведённых функций выполняет вычисление количества расстановок при переданных в программу *m* и *n*. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,191 @@ | ||
.model small | ||
|
||
.stack 24 ;bytes, 10 - word - stack depth for func_uint32OUT, 2 - for funclion call | ||
|
||
.data | ||
;Constants | ||
msg_enterM_err db 0Ah,'"m" must be above "n"! ' | ||
msg_enterM db 0Ah,'Enter "m": $' | ||
msg_enterN_err db 0Ah,'"n" must be above or equal 0! ' | ||
msg_enterN db 'Enter "n": $' | ||
msg_result db 0Ah,'Result: $' | ||
msg_calc_error db 0Ah,'The result is too big!',0Ah,'Further calculation is not possible.$' | ||
func_uint16IN_errmsg db 0Ah,'Invalid input! Enter 16-bit unsigned number: $' | ||
func_div32x16_divider dw 10 | ||
;Multithread non-safe | ||
func_uint16IN_buffer db 6, 0, 6 dup(?) | ||
|
||
.code | ||
start proc | ||
mov ax, @data | ||
mov ds, ax ;init data segment | ||
lea dx, msg_enterN | ||
N_reenter: | ||
mov ah,9 | ||
int 21h ;message print | ||
call func_uint16IN ;input number | ||
test ax,ax | ||
jz N_unc | ||
mov di,ax ;di = n | ||
lea dx, msg_enterM | ||
M_reenter: | ||
mov ah,9 | ||
int 21h ;message print | ||
call func_uint16IN ;input number | ||
cmp ax,di | ||
jb M_unc | ||
je N_decrease | ||
next1: | ||
xor dx,dx ;dx - result high word | ||
sub di,1 | ||
jbe displ_result ;jump to skip loop | ||
mov cx,di | ||
mov bx,ax ;bx = m, ax - result low word | ||
cloop: | ||
dec bx | ||
call func_mul32x16 | ||
jc calc_error | ||
loop cloop | ||
displ_result: | ||
mov bx,ax | ||
mov cx,dx ;save registers values | ||
lea dx, msg_result | ||
mov ah,9 | ||
int 21h ;message print | ||
mov ax,bx | ||
mov dx,cx ;restore saved registers values | ||
call func_uint32OUT | ||
mov ah, 4Ch | ||
int 21h ;stop | ||
calc_error: | ||
lea dx, msg_calc_error | ||
mov ah,9 | ||
int 21h | ||
mov ah, 4Ch | ||
int 21h ;stop | ||
N_unc: | ||
lea dx, msg_enterN_err | ||
jmp N_reenter | ||
N_decrease: | ||
dec di | ||
jmp next1 | ||
M_unc: | ||
lea dx, msg_enterM_err | ||
jmp M_reenter | ||
start endp | ||
|
||
;require: ax, bx, cx, dx, si | ||
func_uint16IN proc | ||
mov bx,10 ;prepare bx register | ||
xor ch,ch | ||
label_func_uint16IN_reinput: | ||
lea dx, func_uint16IN_buffer ;set pointer to buffer | ||
mov ah,0Ah ;init string input mode | ||
int 21h ;input string | ||
mov cl, [func_uint16IN_buffer+1] | ||
lea si, func_uint16IN_buffer+2 ;set pointer to first symbol of string to si | ||
xor ax,ax ;zero ax | ||
label_func_uint16IN_loop: | ||
cmp byte ptr [si],'0' ;check symbol code | ||
jb label_func_uint16IN_err | ||
cmp byte ptr [si],'9' ;check symbol code | ||
ja label_func_uint16IN_err | ||
mul bx ;multiply to basis | ||
jc label_func_uint16IN_err | ||
sub byte ptr [si],'0' ;get number from symbol | ||
add al,[si] ;add number to result | ||
adc ah,0 | ||
jc label_func_uint16IN_err | ||
inc si | ||
loop label_func_uint16IN_loop ;string to uint16 cycle | ||
ret | ||
label_func_uint16IN_err: | ||
lea dx,func_uint16IN_errmsg | ||
mov ah,9 | ||
int 21h | ||
jmp label_func_uint16IN_reinput | ||
func_uint16IN endp | ||
|
||
;require: ax, bx, cx, dx, si, di | ||
func_uint32OUT proc | ||
;ax - low word | ||
;dx - high word | ||
xor cx,cx ;zero counter | ||
label_func_uint32OUT_decodeNext: | ||
inc cx ;count digits | ||
call func_div32x16 ;get digit | ||
push bx ;save digit | ||
test ax,ax ;check that digits not finish | ||
jnz label_func_uint32OUT_decodeNext ;if not - repeat | ||
test dx,dx | ||
jnz label_func_uint32OUT_decodeNext ;if not - repeat | ||
mov ah,2 ;prepare DOS output | ||
label_func_uint32OUT_printNext: | ||
pop dx ;get digit | ||
add dx,'0' ;set digit to output | ||
int 21h | ||
loop label_func_uint32OUT_printNext | ||
ret | ||
func_uint32OUT endp | ||
|
||
;require: ax, bx, dx, si, di | ||
func_mul32x16 proc | ||
;ax - low word | ||
;dx - high word | ||
;bx - multiplier | ||
mov si,ax ;prepare to high word multiply | ||
mov ax,dx | ||
mul bx | ||
jo label_func_mul32x16_overflow | ||
mov di,ax | ||
mov ax,si ;prepare to low word multiply | ||
mul bx | ||
add dx,di | ||
jc label_func_mul32x16_overflow | ||
ret | ||
label_func_mul32x16_overflow: | ||
stc | ||
ret | ||
func_mul32x16 endp | ||
|
||
;require: ax, bx, dx, si, di | ||
func_div32x16 proc | ||
;ax - low word input | ||
;dx - high word input | ||
;func_div32x16_divider - divider | ||
;ax - low word quotient | ||
;dx - high word quotient | ||
;bx - remainder | ||
test dx,dx | ||
jz func_div32x16_simpleDiv | ||
mov di,dx ;LW block - save high word | ||
xor dx,dx | ||
div [func_div32x16_divider] ;divide low word | ||
mov bx,ax ;save quotient low word | ||
mov si,dx ;save remainder low word | ||
mov ax,di ;HW block | ||
xor dx,dx | ||
div [func_div32x16_divider] ;divide high word | ||
mov di,ax ;save quotient high word | ||
xor ax,ax ;HWR block | ||
div [func_div32x16_divider] ;divide high word remainder | ||
add bx,ax | ||
adc di,0 | ||
mov ax,dx ;R block | ||
xor dx,dx | ||
add ax,si ;remainder summ | ||
adc dx,0 | ||
div [func_div32x16_divider] ;divide remainder summ | ||
add ax,bx | ||
adc di,0 | ||
mov bx,dx ;result forming | ||
mov dx,di ;high word to bx | ||
ret | ||
func_div32x16_simpleDiv: | ||
div [func_div32x16_divider] | ||
mov bx,dx | ||
xor dx,dx | ||
ret | ||
func_div32x16 endp | ||
|
||
end start |
Oops, something went wrong.