Отправляет email-рассылки с помощью сервиса Sendsay
  Все выпуски  

RFpro.ru: Ассемблер? Это просто! Учимся программировать


Хостинг портала RFpro.ru:
Московский хостер
Профессиональный ХОСТИНГ на базе Linux x64 и Windows x64

РАССЫЛКИ ПОРТАЛА RFPRO.RU

Лучшие эксперты данной рассылки

Boriss
Статус: Академик
Рейтинг: 2587
∙ повысить рейтинг »
Абаянцев Юрий Леонидович aka Ayl
Статус: Профессионал
Рейтинг: 2207
∙ повысить рейтинг »
vladisslav
Статус: 8-й класс
Рейтинг: 1322
∙ повысить рейтинг »

/ КОМПЬЮТЕРЫ И СОФТ / Программирование / Assembler (Ассемблер)

Номер выпуска:1402
Дата выхода:19.12.2010, 00:00
Администратор рассылки:Лысков Игорь Витальевич (Старший модератор)
Подписчиков / экспертов:224 / 67
Вопросов / ответов:3 / 3

Вопрос № 181212: Здравствуйте, уважаемые эксперты! Прошу Вас ответить на следующий вопрос: реализовать функцию 6 прерывания int 30h. В приложении модуль на Pascal (используются ассемблерные вставки). Там функция 6 реализована, однако, преподаватель сказал что реализ...


Вопрос № 181328: Здравствуйте, уважаемые эксперты! Прошу Вас помочь с решением следующей задачи: Разработать подпрограмму, которая разбивает заданную строку на две части: первое слов (до первого пробела) и остальная часть строки (пробелы в начале строки убира...
Вопрос № 181333: Здравствуйте, требуется реализовать следующий алгоритм: 1.Дано число(В данном случаи 30); 2.Проверяем сколько раз выполнился алгоритм. 3.Если меньше заданного количества и число четное, то делим на 2. Если не четное, умножаем на 3 и приба...

Вопрос № 181212:

Здравствуйте, уважаемые эксперты! Прошу Вас ответить на следующий вопрос: реализовать функцию 6 прерывания int 30h. В приложении модуль на Pascal (используются ассемблерные вставки). Там функция 6 реализована, однако, преподаватель сказал что реализована она "коряво", прошу Вас предложить вариант получше. Искренне благодарю за помощь!

Отправлен: 10.12.2010, 20:19
Вопрос задал: Alexkharkov (Посетитель)
Всего ответов: 1
Страница вопроса »


Отвечает Лысков Игорь Витальевич (Старший модератор) :
Здравствуйте, Alexkharkov!
Вот Вам реализация функций 5 и 6
В функции 5 сдвигаем edx влево так, чтобы наше число стало на левом крае регистра,
затем выводим по тетрадам (раз Вам так хочется менять атрибут у тетрад), начиная со старшего бита
В функции 6 мы сначала обнуляем старшие ненужные биты, сдвигая влево/вправо на число ненужных бит,
затем формируем в стеке последовательность цифр, как остатки от деления на 10 нашего числа,
ну и, наконец, выводим на экран цифры из стека в обратном порядке.

Код:
{-------Функция 5: вывод данных на экран в двоичной форме-----}
{ AL=0 - вывод байта }
{ AL=1 - вывод слова }
@f5: { AL=2 - вывод двойного слова }
cmp modeVA,0 { определимся с атрибутом }
jz @51
mov ah,0f0h { для ч/б }
jmp @52
@51:
mov ah,cl { заданный атрибут }
@52:
mov cl,al { размерность данных }
mov bx,8 { 8 бит на байт }
shl bx,cl { всего бит }
mov cx,32 { максимум бит }
sub cx,bx { число "лишних" бит слева }
db 66h
shl dx,cl { сдвинем edx влево, убрав все лишние }
mov cx,bx { сколько выводим бит }
shr cx,2 { сколько тетрад }
@lp_1:push cx { цикл вывода тетрад }
xor ah,8 { "помигаем" атрибутом для тетрад }
mov cx,4 { число бит в тетраде }
@lp_2: { цикл вывода терады, начиная со ст бита }
mov al,0 { обнулим }
db 66h { сдвинем edx на 1 бит влево, }
shl dx, 1 { при этом старший бит будет в C }
adc al,'0' { al = 0+'0'+C (в итоге '0' или '1') }
stosw { пишем }
loop @lp_2 { биты тетрады }
pop cx { счетчик тетрад }
loop @lp_1 { по всем }
add di,2 { пропустим одно знакоместо (если надо) }
jmp @end

{-----Функция 6: вывод данных на экран в десятичной форме-----}
{ AL=0 - вывод байта }
{ AL=1 - вывод слова }
@f6: { AL=2 - вывод двойного слова }
cmp modeVA,0 { определимся с атрибутом }
jz @61
mov bl,0f0h { для ч/б }
jmp @62
@61:
mov bl,cl { заданный атрибут }
@62:
mov cl,al { размерность данных }
mov ax,8 { 8 бит на байт }
shl ax,cl { всего бит }
mov cx,32 { максимум бит }
sub cx,ax { число "лишних" бит слева }
db 66h
shl dx,cl { сдвинем edx влево, убрав все лишние }
db 66h
shr dx,cl { вернем обратно, при этом вместо лишних будут 0 }
db 66h
mov ax,dx { наше число }
xor cx, cx { число цифр }
db 66h
mov si, 10 { будем делить на dword 10 }
dw 0
@6_1: { цикл получения цифр }
db 66h
xor dx,dx { подготавливаемся к делению }
db 66h
div si { edx:eax / 10 }
push dx { сохраним остаток - очередную младшую цифру }
inc cx { считаем }
db 66h
test ax,ax { eax != 0 ? }
jnz @6_1 { т.е. еще есть десятичные разряды? }
@6_2: { цикл вывода цифр в обратном порядке }
pop ax { извлекаем из стека }
mov ah, bl { атрибут }
or al, '0' { 0-9 -> '0'-'9' }
stosw { пишем }
loop @6_2 { по всем }
add di,2 { пропустим одно знакоместо (если надо) }
jmp @end

end

-----
Люби своего ближнего, как самого себя

Ответ отправил: Лысков Игорь Витальевич (Старший модератор)
Ответ отправлен: 18.12.2010, 02:56
Номер ответа: 264865
Украина, Кировоград
Тел.: +380957525051
ICQ # 234137952
Mail.ru-агент: igorlyskov@mail.ru

Вам помог ответ? Пожалуйста, поблагодарите эксперта за это!
Как сказать этому эксперту "спасибо"?
  • Отправить SMS #thank 264865 на номер 1151 (Россия) | Еще номера »
  • Отправить WebMoney:


  • Вопрос № 181328:

    Здравствуйте, уважаемые эксперты! Прошу Вас помочь с решением следующей задачи:

    Разработать подпрограмму, которая разбивает заданную строку на две части: первое слов (до первого пробела) и остальная часть строки (пробелы в начале строки убираются). Разработать программу, которая вводит с клавиатуры строку и выводит каждое слово с новой строки.

    Для решения использовать Tasm без использования директивы model, операционная система ДОС, формат ЕХЕ. Приложите к решению пожалуйста блок-схему.

    Отправлен: 13.12.2010, 19:41
    Вопрос задал: Ivan Afonin (1-й класс)
    Всего ответов: 1
    Страница вопроса »


    Отвечает Лысков Игорь Витальевич (Старший модератор) :
    Здравствуйте, Ivan Afonin!
    Вот программа:
    Код:

    .186 ;чтобы можно было использовать push <число>
    assume cs:code, ds:data, es:data
    code segment para public 'code'
    start:
    mov ax, data
    mov ds, ax
    mov es, ax ;пусть es=ds=data

    lea dx, sString
    mov ah, 9
    int 21h ;ждем строку

    mov bMax, 80 ;задаем максимальное значение строки
    lea dx, bMax
    mov ah, 0ah
    int 21h ;вводим строку

    lea dx, sResult
    mov ah, 9
    int 21h ;выводим заголовок о выводе слов

    mov wAddr, offset bString ;адрес строки
    next:
    push offset wAddr ;адрес адреса строки
    call FirstWord ;разбиваем на подстроки
    test ax, ax ;ax = адресу слова, =0 - одни пробелы
    jz finish ;в конце пробелы - на выход
    mov dx, ax
    mov ah, 9
    int 21h ;выведем слово

    mov ah, 2 ;на новую строку
    mov dl, 0dh
    int 21h
    mov dl, 0ah
    int 21h
    cmp wAddr, 0 ;последнее слово?
    jne next ;продолжаем разбивать строку
    finish:
    lea dx, sPress
    mov ah, 9
    int 21h ;press any key

    mov ah, 8
    int 21h ;ждем any key

    mov ax, 4c00h
    int 21h ;bye

    ;Разбор строки на первое слово и все остальное
    ;Исходная строка портится! В конце слова ставится $ для вывода по 9 функции
    ;Параметр - адрес слова с адресом строки
    ;Возвращается в ax адрес первого слова, в слове с адресом строки
    ; возвращается адрес подстроки, начинающейся за первым словом или 0 для последнего слова
    ppStr equ [bp+4] ;адрес адреса строки
    FirstWord proc
    push bp
    mov bp, sp
    xor cx, cx ;адрес первого слова
    mov bx, ppStr ;адрес адреса строки
    mov si , [bx] ;адрес строки
    SearchBegin: ;цикл разбора строки
    lodsb ;очередной символ
    cmp al, 0dh ;конец строки
    je FW_last ;строка из одних пробелов
    cmp al, ' ' ;пробел?
    je SearchBegin ;первые пробелы обходим
    lea cx, [si-1] ;адрес начала слова
    SearchEnd: ;ищем конец слова
    lodsb ;очередной символ
    cmp al, 0dh ;конец строки
    je FW_last ;последнее слово
    cmp al, ' ' ;конец слова?
    jne SearchEnd ;ищем пробел после слова
    mov byte ptr [si-1], '$' ;поставим вместо пробела '$' для вывода
    jmp FW_ret ;на выход
    FW_last: ;последнее слово или одни пробелы
    mov byte ptr [si-1], '$' ;поставим вместо пробела '$' для вывода
    xor si, si ;больше слов нет
    FW_ret:
    mov [bx], si ;сохраним адрес второй подстроки или 0, если больше слов нет
    mov ax, cx ;возвращаем адрес первого слова для вывода
    pop bp
    ret 2 ;уберем из стека параметр
    FirstWord endp
    code e nds

    data segment para public 'data'
    sString db 0ah,'Enter string: $'
    sResult db 0ah,0ah,'Words:',0dh,0ah,'$'
    sPress db 0dh,0ah,'Press any key$'
    ;буфер для ввода числовой строки (для функции 0ah)
    bMax db ? ;максимальный размер буфера
    bCount db ? ;реальный размер строки
    bString db 80 dup (?) ;сама строка
    wAddr dw ? ;адрес анализируемой строки
    data ends

    end start


    181328-block-sch.doc (43.5 кб)
    -----
    Люби своего ближнего, как самого себя

    Ответ отправил: Лысков Игорь Витальевич (Старший модератор)
    Ответ отправлен: 13.12.2010, 23:10
    Номер ответа: 264745
    Украина, Кировоград
    Тел.: +380957525051
    ICQ # 234137952
    Mail.ru-агент: igorlyskov@mail.ru

    Оценка ответа: 5
    Комментарий к оценке:
    Спасибо :)

    Вам помог ответ? Пожалуйста, поблагодарите эксперта за это!
    Как сказать этому эксперту "спасибо"?
  • Отправить SMS #thank 264745 на номер 1151 (Россия) | Еще номера »
  • Отправить WebMoney:


  • Вопрос № 181333:

    Здравствуйте, требуется реализовать следующий алгоритм:
    1.Дано число(В данном случаи 30);
    2.Проверяем сколько раз выполнился алгоритм.
    3.Если меньше заданного количества и число четное, то делим на 2.
    Если не четное, умножаем на 3 и прибавляем 1.
    org 0x100
    call sub_1 ;Субрутина в которой указано, что ax-30
    call sub_2 ;Сравниваем счетчик с числом

    mov ah,8
    int 0x21
    mov ah,0x4c
    int 0x21

    sub_1:
    mov ax, 30
    ret
    sub_2:
    mov cx,100
    cmp bx,cx
    JNA label_3 ; Если счетчик меньше 100
    ;Если Больше 100, выйти из субрутины к строчке 5.
    label_3:
    cmp ax,1 ;Если равно 1 то
    je exit ;выходим
    TEST AX, 1 ;Если не равно проверяем на четность
    JNZ label_2 ;Если не четное то прыгаем на label_2 иначе выполняем
    Label_1
    label_1:
    ;В реализации этого блока нужна помощь
    mov si,2
    mov dx,0
    div si
    inc bx
    JMP label_3
    label_2:
    ;В реализации этого блока нужна помощь
    mov si,3
    mul si< br> add dl,1
    inc bx
    JMP label_3
    exit:
    ret ;Возвращает на строку 5
    Заранее спасибо, с нетерпением жду ответа!

    Отправлен: 13.12.2010, 21:46
    Вопрос задал: CyberGod (Посетитель)
    Всего ответов: 1
    Страница вопроса »


    Отвечает Лысков Игорь Витальевич (Старший модератор) :
    Здравствуйте, CyberGod!
    Вот Вам ответ
    Код:
    ;1.Дано число(В данном случаи 30);
    ;2.Проверяем сколько раз выполнился алгоритм.
    ;3.Если меньше заданного количества и число четное, то делим на 2.
    ;Если нечетное, умножаем на 3 и прибавляем 1.
    .model tiny
    .code
    .startup

    call sub_1 ;Субрутина в которой указано, что ax=30
    call sub_2 ;Сравниваем счетчик с числом

    mov ah, 8
    int 21h
    mov ah, 4ch
    int 21h

    sub_1:
    mov ax, 30
    ret

    sub_2:
    xor bx, bx ;Будем в bx считать число проходов алгоритма
    label_4:
    cmp ax, 100
    JNA label_3 ;Если счетчик меньше 100
    exit :
    mov ax, bx
    ret ;Если Больше 100, выйти из субрутины
    label_3:
    cmp ax, 1 ;Если = 1 то
    je exit ;выходим
    TEST AX, 1 ;Если > 1 проверяем на четность
    JNZ label_2 ;Если нечетное то прыгаем на label_2 иначе выполняем Label_1
    label_1: ;четное
    shr ax, 1 ;делим на 2 сдвигом на 1 бит вправо
    inc bx ;считаем
    JMP label_4 ;на проверку
    label_2: ;нечетное
    mov si, 3
    mul si ;*3
    inc ax ;*3 + 1
    inc bx ;считаем
    JMP label_4 ;на проверку

    end

    -----
    Люби своего ближнего, как самого себя

    Ответ отправил: Лысков Игорь Витальевич (Старший модератор)
    Ответ отправлен: 13.12.2010, 23:43
    Номер ответа: 264748
    Украина, Кировоград
    Тел.: +380957525051
    ICQ # 234137952
    Mail.ru-агент: igorlyskov@mail.ru

    Оценка ответа: 5

    Вам помог ответ? Пожалуйста, поблагодарите эксперта за это!
    Как сказать этому эксперту "спасибо"?
  • Отправить SMS #thank 264748 на номер 1151 (Россия) | Еще номера »
  • Отправить WebMoney:


  • Оценить выпуск »
    Нам очень важно Ваше мнение об этом выпуске рассылки!

    Задать вопрос экспертам этой рассылки »

    Скажите "спасибо" эксперту, который помог Вам!

    Отправьте СМС-сообщение с тестом #thank НОМЕР_ОТВЕТА
    на короткий номер 1151 (Россия)

    Номер ответа и конкретный текст СМС указан внизу каждого ответа.

    Полный список номеров »

    * Стоимость одного СМС-сообщения от 7.15 руб. и зависит от оператора сотовой связи. (полный список тарифов)
    ** При ошибочном вводе номера ответа или текста #thank услуга считается оказанной, денежные средства не возвращаются.
    *** Сумма выплаты эксперту-автору ответа расчитывается из суммы перечислений на портал от биллинговой компании.


    © 2001-2010, Портал RFPRO.RU, Россия
    Авторское право: ООО "Мастер-Эксперт Про"
    Автор: Калашников О.А. | Программирование: Гладенюк А.Г.
    Хостинг: Компания "Московский хостер"
    Версия системы: 2010.6.25 от 13.12.2010

    В избранное