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

Ассемблер? Это просто! Учимся программировать (FAQ)


Служба Рассылок Subscribe.Ru проекта Citycat.Ru

Ассемблер? Это просто! Учимся программировать (FAQ)
______________________________________

Выпуск N 067

Вопросы, которые поступили от подписчиков рассылки
"Ассемблер? Это просто! Учимся программировать"

Дата выхода: 2001-08-23


Вопрос №577

Уважаемые эксперты, я получил отклик на свой предыдущий вопрос и очень вам блогодарен.
Но я видимо выразился очень расплывчито поэтому сейчас постораюсь исправить ошибку.
Цель моей программы: При запуске пользователем какого либо файла моя программа резедент
должна записывать имя этого вайла в текстовый файл gurnal.txt.
Но программа написанная мной вешает системму.
Я пытался исправить код рабочей программы которая пришла в рассылке с номером 010"Учись программировать на ассемблере"
Я очень пршу откликнутьсяя быстрее.
мой адрес: post@arh.ru
CSEG segment
assume ss:CSEG,cs:CSEG,es:CSEG,ds:CSEG
org 100h
Begin:
jmp Init
;Начало резедента
MOY proc
pushf
cmp ah,3Dh; если открыт какой либо файл на выполнение то выполнить следующие функции
je Ok_3Dh
popf ;Иначе отдать упровление DOS
jmp dword ptr cs:[VECT]
Ok_3Dh:
push dx;Предпологаю что здесь будет имя открытого программой файла
mov ax,3d02h ;открыть файл для записи
mov dx,offset file_nam ;Имя файла куда производиться запись
int 21h
mov hahdle,ax
mov dx,ax
mov cx,30
pop dx
mov dx,offset dx ;что записываем в файл. Запишем в файл gurnal.txt имя файла который запустит пользователь во время работы
int 21h
mov ah,3eh ;закроем файл
mov dx,handle
int 21h
iret
Handle dw 0
VECT dd ?
file_nam db 'gurnal.txt',0
MOY endp
;конец резедента
Init:
mov ax,3521h
int 21h
mov word ptr VECT,bx
mov word ptr VECT+2,es
mov ax,2521h
mov dx,offset MOY
int 21h
mov dx,offset Init
int 27h
CSEG ends
end Begin

Ответ

Уважаемый fagot!
если вы вдруг не обратили внимания (что то мне не спиться... ;( ), то в обработчике прерывания int 21h все сегментные регистры меняются, "своим" остается токо cs, а ds, ss, es - все "чужие", поэтому в dx то может и содержиться имя файла, но ds совсем не тот что нада.... а там, по этому адресу, как назло ближайший нолик может быть $ер знает де!


Отправил эксперт: Broken Sword (www.revolution.co.uk - скрытая реклама...)
Эксперт отправил ответов (всего): 70

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №584

оПХБЕР!
мЮПНД, ОНДЯЙЮФХРЕ ОНФЮКСИЯРЮ НОХЯЮМХЪ ТСМЙЖХИ

mov ax,0b1xxh
int 1ah

ДКЪ СЯРПНИЯРБ PCI.
C СБ. бНХМЯРБСЧЫХИ КЮЛЕП.

Ответ

Здравствуйте, бНХМЯРБСЧЫХИ КЮЛЕП!

Это интерфейс pci BIOS.
Подробнее можно посмотреть в интеррапт листе Ральфа Брауна...
Там их несколько десятков функций!!!


Отправил эксперт: Dron (http://spawnhole.narod.ru/asmos/asmos.html - Операционная система с нуля!)
Эксперт отправил ответов (всего): 69

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №572

Уважаемые эксперты.
Помогите решить проблемму.
Нужно создать резедент под DOS.
Он должен записывать в текстовый файл имя и дату/время любово запускаемого файла.
Я прелагаю код. Но он при запуске вкшает ПК.
Оччень прошу помогите. Не дайте вылететь с работы.
CSEG segment
assume ss:CSEG,cs:CSEG,es:CSEG,ds:CSEG
org 100h
Begin:
jmp Init

MOY proc
pushf
cmp ax,3D00h
je Ok_09h
cli
popf
jmp dword ptr cs:[VECT]
Ok_09h:
push ds
push dx
push cs
pop ds
mov dx,offset May_String
pushf
call dword ptr cs:[Vect]
pop dx
pop ds
popf
sti
iret
VECT dd ?
May_String db'Ђ ў®в ®Ў« ¬ЁвҐбм$'
MOY endp

Init:
mov ax,3521h
int 21h;’ҐЇҐам ¬л §­ Ґ¬ ўҐЄв®а 21 ЇаҐалў ­Ёп ES:BX
mov word ptr VECT,bx
mov word ptr VECT+2,es
;Ђ¤аҐб ўҐЄв®а  б®еа ­Ё«Ё
mov ax,2521h
mov dx,offset MOY;DX ¤®«¦Ґ­ гЄ §лў вм ­  ­ и ®Ўа Ў®взЁЄ
int 21h
mov dx,offset Init
int 27h
CSEG ends
end Begin

Ответ

Здравствуйте, fagot!

Правильно вешает. Существует такое понятие реентерабельности DOS


Вот, собственно, предлагаю готовый исходник
После некоторой правки
Он будет работать как нужно
Удачи! UFO!

Приложение:


Отправил эксперт: UFO
Эксперт отправил ответов (всего): 1

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №586

Уважаемый Broken Sword.
Жаль, что Вы так много потратили своего ночного времени. Его же можно было использовать и иначе!!! %))))
Все тривиально просто. Работа с прерываниями довольно таки проста и допускать здесь ошибки просто...
Во-первых, почему это нельзя менять сегментные регистры: МОЖНО и НУЖНО, только их еще и ВОССТАНАВЛИВАТЬ надо...
Во-вторых, DOS не реентерабелен и желательно проверять а не я сам ли вызвал прерывание (касается fagot!).
В-третьих, причем здесь DTA? Если как временный буфер то ладно, но если как дескриптор файла (Disk Transfer Address), то это глупо, пусть система использует какой-нить свой DTA. Это всегда работало.

Высылаю прогу (работающую), сохраняющую в файле DATA.TXT имя файла для запроса на открытие (во завернул) в 21h.

С путем разберетесь, Некрасивое место количество сохраняемых байт (желательно посчитать кол-во байт до нуля в DS:DX) и писать не создавая файл, а дописывая (вот здесь то флаг и понадобится)...

Если я что-то не так понял, сообщите...
С уважением Ejik.

.model tiny
.286
.code
Locals @@

org 2Ch
envseg dw ?
org 100h
start:
old_int21h:
jmp short init
dw ?
Flag db 0

int21h_handler proc
cmp ah,3Dh
jnz short @@exit
cmp cs:Flag, 0
jnz short @@exit

pusha
push ds
; cli

push cs ;!!!
pop ds
inc Flag ; We must know: is it ours?

mov ah,3Ch ; Creating DATA.TXT
xor cx,cx
push dx
mov dx,offset filename
int 21h
jc @@Bad
xchg ax, bx ; fileHandle

pop dx ; Filename
pop ds
push ds
mov ah,40h
mov cx,128
int 21h

mov ah,3Eh ; Close
int 21h
; sti
@@Bad:
pop ds
popa
dec byte ptr cs:Flag
@@exit:
jmp dword ptr cs:old_int21h
filename db 'c:\data.txt',0

int21h_handler endp

Init: mov ax,3521h ;
int 21h ; ФХФ ЧУЕ СУОП
mov word ptr old_int21h,bx
mov word ptr old_int21h+2,es
mov ax,2521h
mov dx,offset int21h_handler
int 21h
mov ah,49h
mov es,word ptr envseg
int 21h
mov dx,offset Init
int 27h
end start

P.S. Исправил за ~20 мин...
P.S.S. По поводу Pusha - она не сохраняет сегментных регистров !!!
P.S.S.S. Возможно повторение, модем сбросил в самый ответственный момент. Дополнение: Если хочешь сохранить дату ты должен ее указывать не в регистре, а передать на нее указатель в DS:DX. После pusha она сохраняется в стеке, ее и можешь использовать в качестве данного (4 байта), вычислить на нее DS:DX и снова сохранить в файл. Но это уже совсем другая история... =))))))))))

Ответ

Многоуважаемый Роман! За вашу фразу "кстати, pusha не сохраняет сегментных регистров..." из второго (переработанного и дополненного вопроса ;) ), 24 часа назад я готов был бы выложить круглую сумму наличными (если бы она у меня была ) ),но если угодно могу выслать бутыль пива в любую точку Украины "до востребования".
p.s. насчет фотографии я конечно погорячился... и... уважаемые господа!!! пиша (-ся) (как это выразить можно правильно? ;) ) свои программы, если они "мистически" зависают в самых неожиданных местах, не спешите выкладывать свои наличные, а лучше еще раз хорошенько просмотрите КАЖДУЮ команду в справочнике, начиная с mov и заканчивая enter и leave (кстати, красотой работы последних двух я до сих пор не перестаю удивляться!), и всему найдеться свое логическое объяснения, а насчет пресловутой "нереентабельности" DOS (это откуда словцо то такое умное? ;) - так я до сих пор ничего не понял, (а мусолили эту тему довольно долгое время) а если вы о повторной входимости, то так и скажите
p.s. спасибо Roman, просветили насчет pusha! клянусь больше НИКОГДА, ни при каких обстоятельствах ее НЕ ИСПОЛЬЗОВАТЬ из дурного принципа!
отдельное спасибо Orlando, который также замутил работающую программу... ну и чего еще на последок хочется заметить. порадуемся за человека, которого не выгнали с работы на улицу! :)


Отправил эксперт: Broken Sword (www.revolution.co.uk - скрытая реклама...)
Эксперт отправил ответов (всего): 71

Экспертная группа: Оптимизация программ

Вопрос №589

Привет всем. Помогите, пожалуйста, постичь один вопрос. Эта программа создающая новую папку на desktop-e. cseg segment
assume cs:cseg,ds:cseg,es:cseg
org 100h
begin:
mov ah,39h
mov dx,offset dir
int 21h
ret
dir db 'c:\windows\desktop\new folder'
cseg ends
end begin
Как мне довести её до того чтобы самому вводить строку для новой папки??? Я очень прошу, покажите пример, а я сам разберусь просто я не как не смог сделать это.
Заранее благодарю

Ответ

Здравствуйте, Dima!
... да еще к тому же и не работающая! ну, лови, студент! ;)

прога страшно не оптимизирована, потому как писалась 6 минут (тока за это время можно додуматься всунуть чрезвычайно важную проверку на поддержку этой функции и выводом соотв. сообщения в противном случае...)

Приложение:


Отправил эксперт: Broken Sword (www.revolution.co.uk - скрытая реклама...)
Эксперт отправил ответов (всего): 72

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №589

Привет всем. Помогите, пожалуйста, постичь один вопрос. Эта программа создающая новую папку на desktop-e. cseg segment
assume cs:cseg,ds:cseg,es:cseg
org 100h
begin:
mov ah,39h
mov dx,offset dir
int 21h
ret
dir db 'c:\windows\desktop\new folder'
cseg ends
end begin
Как мне довести её до того чтобы самому вводить строку для новой папки??? Я очень прошу, покажите пример, а я сам разберусь просто я не как не смог сделать это.
Заранее благодарю

Ответ

Здравствуйте, Dima!
Просто используй функцию ввода с клавиатуры, например ah=0ah(int 21h)
Да и в твоей проге ошибка: ты забыл в конец строки поставить 0:
dir db 'c:\windows\desktop\new folder',0


Отправил эксперт: Orlando
Эксперт отправил ответов (всего): 25

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №595

Есть программа - обработчик прерывния от звуковой карты.
Программа использует регистры EAX,EBX и тд, а также команды сопроцессора. Как корректно и коротко сделать вход и выход из прерывания с сохранением/восстановлением всех регистров EXX и регистров сопра?
Да и кстати, может кто знает: Borland C++ 3.1 похоже врет в данной ситуации (сохраняет/восстанавливает не все что использует в подпрограмме типа interrupt в режиме 386/7). Так?

Ответ

Здравствуйте, Andrey!
Команда pushad помещает в стек все регистры общего назначения(т.е. EXX, а остальные только через push), а с регистрами сопроцессора дело иное, т.к. специальных команд помещения их ВСЕХ в стек нет, то можно попытать записать их в переменные или каждый в стек, но дело гнилое!(КОРОТКО НИКАК НЕ ПОЛУЧИТСЯ)

А, вообще, лучше вышли прогу свою, тогда разберемся...


Отправил эксперт: Orlando
Эксперт отправил ответов (всего): 26

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №601

Здравствуйте ув эксперты , напишити свои е-мыльницы , ато замучился уже форму енту заполнять , лучше так буду прямо к вам писмы слать :)

Ответ

Здравствуйте, Dr.Zombie!
Суть рассылки в том, что все эксперты работают, как команда, и если один ошибся, то остальные исправят! Да и по-моему проще один раз заполнить форму и послать, чем десять раз переписывать адрес и большее время тратить на отсылку уймы писем!


Отправил эксперт: Orlando
Эксперт отправил ответов (всего): 27

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №601

Здравствуйте ув эксперты , напишити свои е-мыльницы , ато замучился уже форму енту заполнять , лучше так буду прямо к вам писмы слать :)

Ответ

Здравствуйте, Dr.Zombie!
Не, не пойдет!
Нам за ответы то балы начисляются, а потом будет куча Призов!


Отправил эксперт: Sensey
Эксперт отправил ответов (всего): 87

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №595

Есть программа - обработчик прерывния от звуковой карты.
Программа использует регистры EAX,EBX итд, а также команды сопроцессора. Как корректно и коротко сделать вход и выход из прерывания с сохранением/восстановлением всех регистров EXX и регистров сопра?
Да и кстати, может кто знает: Borland C++ 3.1 похоже врет в данной ситуации (сохраняет/восстанавливает не все что использует в подпрограмме типа interrupt в режиме 386/7). Так?

Ответ

Незнаю врет ли C++ по данному поводу, Andrey, но сохранять перед вызовом ВСЕ регистры ПРОЦА и СОПРОЦА итд впринципе нужно так:
(не знаю варианта короче)

Регистры проца:
pushad (EAX,ECX,EDX,EBX,ESP,EBP,ESI,EDI), кстати, pushad=pusha, но использовать эту команду крайне нерекомендую (просто потому что у меня к ней личная неприязнь и 6 часов убитого даром времени, там выше можешь почитать мою истерию).
push CS,DS,SS,ES,FS,GS (конечно не в строчку, а в столбик)
push ESI,EDI,EBP,ESP (тоже самое)
pushfd - поместить в стек регистр EFLAGS, точно так же pushfd=pushf

Регистры сопроца:
там много команд, сохраняющих регисты и еще много чего, но рекомендую FSAVE приемник, где приемник - область памяти 94 или 108 байт в завис. от разрядности операндов, и к тому же еще и инициализирует FPU да еще и проверяет наличие произошедших и необработанных исключений.

Как это все восстановить? в проце - pop-ами, в сопроце - FRSTOR источник (тот приемник).
вроде все.
сохранено все, ктоме пары флагов в EFLAGS (но они к защищенному режиму вроде)


Отправил эксперт: Broken Sword (www.revolution.co.uk - скрытая реклама...)
Эксперт отправил ответов (всего): 73

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №600

Здравствуйте ув эксперты , напишити свои е-мыльницы , ато замучился уже форму енту заполнять , лучше так буду прямо к вам писмы слать :)

Ответ

Здравствуйте, Dr.Zombie!
mail: CodeBuilder@chat.ru
ICQ: 45249044


Отправил эксперт: Евгений
Эксперт отправил ответов (всего): 11

Экспертная группа: Общие вопросы по программированию на Ассемблере под Win32

Вопрос №595

Есть программа - обработчик прерывния от звуковой карты.
Программа использует регистры EAX,EBX итд, а также команды сопроцессора. Как корректно и коротко сделать вход и выход из прерывания с сохранением/восстановлением всех регистров EXX и регистров сопра?
Да и кстати, может кто знает: Borland C++ 3.1 похоже врет в данной ситуации (сохраняет/восстанавливает не все что использует в подпрограмме типа interrupt в режиме 386/7). Так?

Ответ

Здравствуйте, Andrey!
Для сохранения 32-битных регистров используй PUSHAD и POPAD (аналоги PUSHA и POPA для 32-битных регисров). Сохраняет: EAX, ECX, EDX, EBX, ESP, EBP, ESI, EDI.
И нефиг хранить данные в регистрах сопра - это не есть гуд!


Отправил эксперт: Painbringer
Эксперт отправил ответов (всего): 46

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №601

Здравствуйте ув эксперты , напишити свои е-мыльницы , ато замучился уже форму енту заполнять , лучше так буду прямо к вам писмы слать :)

Ответ

Здравствуйте, Dr.Zombie!
А мыло Клавы Шифер не написать?! Специально же сделали всё по людски, что бы приходило только к кому надо! (кстати какое отношение твой вопрос к "Программированию на Ассемблере под ДОС" имеет, я не знаю!!!


Отправил эксперт: Painbringer
Эксперт отправил ответов (всего): 47

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №603

Эй народ! Отзовитесь!
Уже неделю рассылку не получаю!
В чем дело? Может и нет уж этой рассылки ;-((((((
Успокойте меня и скажите, что это почта задерживается...
ИЛИ КАК ????????????? -=8^[``````

Ответ

Здравствуйте, Zipper!
Если вы видите этот текст, значить у вас всё хорошо ;).....


Отправил эксперт: Painbringer
Эксперт отправил ответов (всего): 48

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Вопрос №603

Эй народ! Отзовитесь!
Уже неделю рассылку не получаю!
В чем дело? Может и нет уж этой рассылки ;-((((((
Успокойте меня и скажите, что это почта задерживается...
ИЛИ КАК ????????????? -=8^[``````

Ответ

Здравствуйте, Zipper!
все таки скорее ИЛИ КАК!!!, т.к. недели полторы назад вышел 30 номер рассылки (XMS память), а до этого он в отпуске был! отакот!


Отправил эксперт: Broken Sword (www.revolution.co.uk - скрытая реклама...)
Эксперт отправил ответов (всего): 74

Экспертная группа: Общие вопросы по программированию на Ассемблере под DOS

Подписаться на рассылки

Рассылки Subscribe.Ru
Ассемблер? Это просто! Учимся программировать
Ассемблер? Это просто! Учимся программировать (FAQ)

Форма подачи вопроса

ВНИМАНИЕ!!! Пожалуйста, НЕ высылайте один вопрос сразу нескольким подгруппам! Дополнения к вопросам, на которые эксперт уже ответил НЕ следует направлять ведущему рассылки (я не успеваю!). Просто скомбинируйте первый вопрос и дополнение к нему, а затем заново отправьте его, используя приведенную ниже форму!

Нажимайте кнопку "Отправить" только ОДИН раз и дождитесь полной загрузки страницы, иначе вопрос будет продублирован!


Ваше имя *:

Ваш e-mail *:

Подгруппы:

Вопрос *:

Прилагаемая программа (если необходимо):


Регистрация в качестве эксперта

Архив выпусков


Ведущий рассылки,

Калашников Олег: Assembler@Kalashnikoff.ru
ICQ No.:
68951340
URL сайта подписчиков: http://www.Kalashnikoff.ru

______________

По вопросам сотрудничества, рекламы и спонсорства обращайтесь:

  1. Публичное размещение материала из рассылки: Cooperation@Kalashnikoff.ru
  2. Реклама на сайте, в книге и рассылках: http://www.Kalashnikoff.ru/Reklama.html, Reklama@Kalashnikoff.ru
  3. Издание книги (спонсорство): Sponsor@Kalashnikoff.ru

Рассылка 'Ассемблер? Это просто! Учимся программировать (FAQ)' Рассылка 'Ассемблер? Это просто! Учимся программировать'


(C) Москва, 2001. Авторское право принадлежит Калашникову О.А. Публичное размещение материала из рассылки, а также его использование полностью или частично в коммерческих или иных подобных целях без письменного согласия автора влечет ответственность за нарушение авторских прав.


http://subscribe.ru/
E-mail: ask@subscribe.ru
Отписаться Рейтингуется SpyLog

В избранное