Народ помогите кто чем может нужно написать прогу для перевода из Восьмеричной системы счисления в Двеннадцатиричную на Асме….Вот Есть код для 8 to 16, а надо 8 to 12title a10.exe — from 8 to 16code segmentassume cs:codemain: mov si,8again: mov bx,0mov dl,’?’call d1mov cx,6next: call kbincmp al,’ ‘jebackmovah,0andal, 00001111bmovdi, axmovax, bxmulsiaddax, dimovbx, axloopnextback:movdl,’=’calld1movdx,bxcallhexwmovdl,’H’calld1callcrlfjmpagain;———- subroutines ————–d1 procmovah,2int 21hretd1 endpkbinproc nearmov ah,1int 21hretkbinendphexprocnearmovax,cs;pushdsmovds, ax; set ds=cspushdxmovbx, offset t1moval, dlclcshral,1shral,1shral,1shral,1xlatb; translatemovdl, alcalld1popaxandal, 00001111bxlatb; translatemovdl, alcalld1;popdsrett1db’0123456789ABCDEF’hexendphexwprocnearmovdi, dxmovdl, dhcallhexmovdx, dicallhexmovdl,’ ‘calld1rethexwendpcrlfprocnearmovdl, 10calld1movdl, 13calld1retcrlfendpcodeendsend main
если еще актуально, я немного откомментировал код и написал процедурку duodec (переводит число в 12-рич. сис. и выводит его на экран)вот измененный код (процудуру hex оставил на память 🙂 )код не компилировал и не отлаживал, написал как есть, поэтому может и не работатьtitle a10.exe — from 8 to 12code segmentassume cs:codemain: mov si,8; 8 так как исходная с-ма восьмеричная (потом будем умножать на 😎 again: mov bx,0; здесь будет введенное число после перевода его из ascii в числоmov dl,’?’call d1; выводим вопросmov cx,6next: call kbin; считываем символcmp al,’ ‘; если пробел, то конец вводаje backmov ah,0; дальше переводим ascii символ, в число (например код ‘1’ равен 0x31 )and al, 00001111b; теперь ax = 1 (сначало было например 0x31)mov di, ax; временно запомним mov ax, bx; временно запомним (ax = bx = 0 на первой итерации цикла)mul si; умножим на si (=8) на ax (=0), ax = 0add ax, di; сложим с введенным числом (0 + 1)mov bx, ax; запомним результатloop next; перейдем на считывание следующего символаback: mov dl,’=’; выводим =call d1mov dx,bxcall hexw; переводим двух байтовое число в hex (и выводим в станд.вывод)mov dl,’H’call d1; выводим Hcall crlf; перевод строкиjmp again; все сначала (новое число);———- subroutines ————–d1 proc; пишем в станд. выводmov ah,2int 21hretd1 endpkbin proc near; читаем со станд. вводаmov ah,1int 21hretkbin endphex proc near; переводим один символ (один байт) в 16-чную с-му mov ax,cs; push dsmov ds, ax ; set ds=cspush dxmov bx, offset t1mov al, dlclcshr al,1shr al,1shr al,1shr al,1xlatb ; translatemov dl, alcall d1pop axand al, 00001111bxlatb ; translatemov dl, alcall d1; pop dsrett1 db ‘0123456789ABCDEF’hex endpduodec proc near; переводим один символ (один байт) в 12-чную с-му mov ax,csmov ds, ax; set ds=csmov bx, offset t2; в bx адрес начала буфера; переводим число в ascii (в 12-чной сис-ме и складываем в буфер в обратном порядке)label0:movax, dx; в ax числоcdqidiv 12; делим число на 12 (получаем ah – остаток, al – частное)cmpah, 9; сравним, если число <= 9, то прибавим '0' иначе 'a'jlelabel1addah, 87;число - 10 + 'a' movbyte ptr [bx], ah ; запишем в буферjmplabel2label1:addeax, 48; число + '0'movbyte ptr [bx], ah ; запишем в буферlabel2:addbx, 1; увеличим указатель на буфер на 1mov dx, al; запишем частное от деления cmpdx, 0; проверим на 0 и если не равно, еще один циклjg label0; выводим буфер на печать в обратном порядке (на печать выходит в прямом)label4:subbx, 1; уменьшим указатель на буфер, так сейчас он указывает за последнуюю буквуxor dx, dxmovdl, byte ptr [bx] ; в dl буква по указателюcall d1; выводим букву в станд. вывод (на экран например)mov ax, offset t2cmpax, bx; проверим не дошли ли мы до начала буфераjnelabel4; цикл еще разretbf db ' '; буфер, достаточный для размещения строки результатаduodec endphexw proc near; переводим два символа (dx содежит число)call duodecmov dl,' 'call d1rethexw endpcrlf proc near; перевод строкиmov dl, 10call d1mov dl, 13call d1retcrlf endp
что то не работает, выдает несколько ошибок, в том числе и в последней строчке которой не существует, может кто еще чем помочь может???? Все равно большое спасибо!
а чем компилируешь, tasm, masm? какая ось? я тоже может попробую, если время и асм найду.только сейчас заметил, строчка bf db ‘ ‘; буфер, достаточный для размещения строки результатаужалась, между ‘ ‘ должно быть много пробелов, штук 20 например (чтобы число влезло)
компилирую тасмом…что то все равно ничего не получается..(((
Наконец-то появилось время (суббота 🙂 ) Если все еще актуально, вот работающая версия (под Windows).Компилировал [link url='http://wasm.ru/baixado.php?mode=tool&id=230'] Tasm32(5.3) [/link], отлаживал [link url='http://wasm.ru/baixado.php?mode=tool&id=89'] odbg(1.10) [/link]Скомпилировать проще всего так:1. Распаковать Tasm в какую-нибудь дир., например d:\bin\tasm2. В дир. Examples создать дир. duodec3. В дир. duodec создать файл duodec.asm с исходным кодом4. Тут же (в duodec) создать файл duodec.def5. B тут же создать файл make.batДля компиляции выполнить make.batПосле запуска программа выводит знак ‘?’. Дальше можно ввести 8-ричное число (цифры должны быть меньш 😎 После ввода числа нужно ввести пробел. Программа распечатает число в 12-рич. сис. счисл.Пример работы:D:\bin\tasm\EXAMPLE\duodec>duodec.exe? 0 = 0D:\bin\tasm\EXAMPLE\duodec>duodec.exe? 1 = 1D:\bin\tasm\EXAMPLE\duodec>duodec.exe? 7 = 7D:\bin\tasm\EXAMPLE\duodec>duodec.exe? input error: digit must be less or equal 7!D:\bin\tasm\EXAMPLE\duodec>duodec.exe? 10 = 8D:\bin\tasm\EXAMPLE\duodec>duodec.exe? 14 = 10Как видим, переход на десяток в восмеричной системе происходит на 8-ми (10 = 😎 А переход на 10 в 12-рич. системе происходит при 12 (14 в восмерич.) (14 = 10)Файл duodec.def:CODE PRELOAD MOVEABLE DISCARDABLEDATA PRELOAD MOVEABLE MULTIPLEHEAPSIZE 65536STACKSIZE 65536Файл make.bat:@echo offcls..\..\BIN\tasm32 /mx /m4 /z duodec.asm..\..\BIN\tlink32 -x -V4.0 -Tpe -ap -c duodec.obj,duodec,,,duodec.defif errorlevel == 1 goto failuredel *.objecho duodec.exe createdgoto end:failureecho error!:endpauseФайл duodec.asm:.386.model flat, stdcalllocalsincludelib ..\..\LIB\imp32i.libinclude ..\..\INCLUDE\w32.inc;extrnprintf: PROCextrn_getch: PROCextrn _putch: PROC;.DATAbufdb 32 dup(?) quest db “? “, 0fmtSdb “%s”, 0fmtDdb “%d”, 0equaldb ” = “, 0errMdb”input error: digit must be less or equal 7!”, 0.DATA?;.CODEstart:pushad; сохраним регистрыmov si, 8; так как исходная с-ма восьмеричная (потом будем умножать на 8 )mov ebx, 0; здесь будет введенное число после перевода его из ascii в числоcall printf, offset quest ; выводим ‘?’add esp, 4; восстановим стекnext:mov eax, 0; обнулим eaxcall_getch; ожидаем ввода символа cmp ax, 20h; если пробел, то конец вводаje endinput; переходим на преобразование числаmov ah, 0 ; дальше переводим ascii символ, в число (например код ‘1’ равен 0x31 )and al, 00001111b ; теперь ax = 1 (сначало было например 0x31)mov di, ax ; временно запомним cmp ax, 7; если введенная цифра больше 7, то ошибкаjle cont; переход на продолжние работыcall printf, offset errM ; печатаем сообщение об ошибкеadd esp, 4; восстанавливаем стекjmp exit; переход на конец программыcont:call printf, offset fmtD, eax; печатаем очередную введенную цифруadd esp, 8; восстанавливаем стекmov ax, bx ; временно запомним bxmul si ; умножим ax на 8 (si = 😎 add ax, di ; сложим с уже введенным числом (накапливаем сумму)mov bx, ax ; запомним результатloop next ; перейдем на считывание следующего символаendinput:call printf, offset equal ; выводим знак ‘=’add esp, 4; восстановим стекmov edx, ebx; введенное число в dxcall duodec; преобразуем и печатаем число в 12-рич. системуexit:popad; восстановим регистрыcallExitProcess, 0; вызов завершения программы (в Windows)ret; конец программы;;proc – подпрограмма, перевод числа в dx в 12-чную с-му и вывод на экранduodec: mov ebx, offset buf ; в bx адрес начала буфера; переводим число в ascii (в 12-чной сис-ме и складываем в буфер в обратном порядке)label0:mov si, 12; будем делить на 12mov ax, dx; число в axsub dx, dx; преобразуем AX в двойное слово в AX:DXdiv si ; делим число на 12 (получаем dx – остаток, ax – частное)cmp dl, 9 ; сравним, если число <= 9, то прибавим '0' иначе 'a'jle label1add dl, 87 ;число - 10 + 'a' mov byte ptr [ebx], dl ; запишем букву в буферjmp label2label1:add dl, 48 ; число + '0'mov byte ptr [ebx], dl ; запишем букву в буферlabel2:add bx, 1 ; увеличим указатель на буфер на 1mov dx, ax; частное в dx cmp dx, 0 ; проверим на 0 и если не равно, еще один циклjg label0; выводим буфер на печать в обратном порядке (на печать выходит в прямом)label4:sub bx, 1 ; уменьшим указатель на буфер, так сейчас он указывает за последнуюю буквуxor edx, edx; обнуляем edxmov dl, byte ptr [ebx] ; в dl буква по указателюcall _putch, edx; выводим букву в станд. вывод (на экран например)add esp, 4; восстанавливем стекmov eax, offset buf; в ax начало буфераcmp eax, ebx ; проверим не дошли ли мы до начала буфераjne label4 ; если нет, цикл еще разret; конец подпрограммыEND start
Огромнейшее спасибо, пробую откомпилировать…
-sc-, Что то не могу откомпилировать…говорит ошибка…может как нибудь Экзэшник перекинуть можно??? на мыло например?
Так вроде откомпилировал, но вот после нажатия пробела….вылетает из проги…что это может быть???
так вроде как прогу запустить разобрался, только вот приходится для перевода каждого числа заново запускать прогу…почему выходит? и почему включая семерку и выше не переводит??
Семерку она переводит 7 = 7, и 77 тоже переведет. В восьмеричной системе одна цифра не может быть больше 7. Т.е. 77 нормально, а 78 уже нет. Про системы счисления немного написано в вики. Искать гуглом по словам: wiki системы счисления.Программку написал только для перевода одного числа, но если надо больше то вот. Весь текст не привожу,только три кусочка и куда вставить. Чтобы выйти, нужно ввести “неправильный” символ, например Enter.добавим строчку crlf … вот так:errMdb “input error: digit must be less or equal 7!”, 0crlf db 13, 10, 0.DATA?добавми строчку again: вот так:.CODEstart:pushad; сохраним регистрыagain:mov si, 8; так как исходная с-ма восьмеричная (потом будем умножать на 8 )и еще пару строчек вот так:call duodec; преобразуем и печатаем число в 12-рич. системуcall printf, offset crlf ; перевод строкиadd esp, 4 ; восстановим стекjmp againexit:
Насчет проблем компиляции не знаю. Никаких не было. Путь к tasm32 нужно прописать в переменную окружени path. Tasm у меня такойD:\bin\tasm\EXAMPLE\duodec>tasm32Turbo Assembler Version 5.0 Copyright (c) 1988, 1996 Borland InternationalВинда XP. Tasm брал на wasm.ru[link url='wasm.ru'] wasm’е [/link] в разделе компиляторы [link url='http://wasm.ru/baixado.php?mode=tool&id=230'] Tasm5+ [/link].
Все спасибо большое, не знаю что бы я без вас делал, все сдал….зачет поставил!!! 🙂 🙂
Повезло, что препод форум не читает 🙂
Вопрос не касается первоначального сообщения, но касается ассемблера.Сразу скажу, что это программа учебная, используется ассемблер для DOS, конкретнно – tasm 3.0Условие такое: имеется две переменныеvar1 db ‘1234567890$’var2 db ‘0987654321$’В определенный момент необходимо присвоить переменной var1 значение переменной var2. Делаю так:mov AX, offset var1mov var2, AXПри компиляции выдает ошибку: Operand types do not match, указывается номер второй строки, в которой пытаюсь в переменную записать из регистра…. Как правильно сделать копирование одной переменной в другую?
Copyright ©