Задача: Написать прогу, которая через определенный промежуток времени запускает другую прогу. Реализовать через будильник. Реализация: Код (Text): Code Segment Assume CS:CODE, DS:CODE, SS:CODE org 100h .386 Main proc jmp Init ;data FILENAME DB 'D:\lab3d.exe',0 ;загружаем TRIAL.EXE Seconds DB 5h Minutes DB 0 Hours DB 0 PARAMETERS DW 7 DUP(0) ;нулевой блок параметров KEEP_SS DW 0 ;переменная для SS KEEP_SP DW 0 ;переменная для SP ;resident code Entry: ;---перераспределение памяти mov dx,(Init-Main+100h+0fh)/16 MOV AH,4AH ;номер функции INT 21H ;перераспределение ;---указываем на блок параметров MOV AX,DS ;в ES - сегмент MOV ES,AX ; MOV BX,OFFSET PARAMETERS ;в BX - смещение ;---сохранить копии SS и SP MOV KEEP_SS,SS ;сохраняем SS MOV KEEP_SP,SP ;сохраняем SP ;---указываем на строку имени файла MOV DX,OFFSET FILENAME ;смещение - в DX MOV DS,AX ; ;---загрузка программы MOV AH,4BH ;функция EXEC MOV AL,0 ;выбираем "загрузку и запуск" INT 21H ;запускаем задачу ;---впоследствии, восстанавливаем регистры MOV SS,KEEP_SS ;восстанавливаем SS MOV SP,KEEP_SP ;восстанавливаем SP iret Main endp init proc ;---замена прерывания--------------------------------- mov ah,25h mov al,4ah lea dx,Entry int 21h ; int 4ah ;---сбрасываем будильник------------------------------ mov ah,07h int 1ah ;---устанавливаем будильник-------]-------------------- mov ah,06h mov ch,hours mov cl,minutes mov dh,seconds int 1ah ;---выгружаемся---------------------------------------- mov ax,3100h mov dx,(Init-Main+100h+0fh)/16 int 21h init endp Code ends end Main используем тег [ code ]! Не работает... И судя по всему не срабатывает будильник. Потому что просто вызов прерывания результативен. Люди добрые, помогите! Задача проще некуда, а столько мучаюсь!
Попробуй проверять флаг CF после установки будильника. Если установлен, значит произошла ошибка. Ещё перед смелым вызовом DOS из обработчика прерывания, хорошо бы проверять её занятость. Посмотри описания INT 28h и INT21,AH=34H Возможно дело в этом.
Я не знаю насколько я прав но у меня тема с mov ax,3100h mov dx,(Init-Main+100h+0fh)/16 int 21h Еще не разу не срабатывала ... Может в винде дело не знаю... Касательно проги: На всякий п.. сбрось i флаг при входе в обработчик, может просто прерывания запрещены...
To Vov4ick: Спасибо друг, сам разобрался. Я идиот, думал что нужно указывать время через которое срабатывает, а не в которое. И это при том что програмировал будильник в прошлом году на С++.
Проверяй занятость DOS, и в обработчике неплохо бы все регистры сохранять и восстанавливать, а то работает программка какая-то, вдруг - раз - все регистры поменялись :-O
Мда... Из под TurboShell работает, но по завершению запущеной проги выдаёт сообщение Null Pointer Assignment. Из под ДОС вообще ничего не запускает, а точнее зависает. Код (Text): .model tiny .data org 100h .386 Main proc jmp Init ;data BUF DB 255 DUP(0) ;переменная для хранения FILENAME DB 'D:\lab3d.exe',0 ;загружаем TRIAL.EXE Seconds DB 17h Minutes DB 55h Hours DB 05h PARAMETERS DW 7 DUP(0) ;нулевой блок параметров KEEP_SS DW 0 ;переменная для SS KEEP_SP DW 0 ;переменная для SP Size dw 0 ;resident code Entry: pusha push es push ds push cs pop ds ;---указываем на блок параметров MOV AX,DS ;в ES - сегмент MOV ES,AX ; MOV BX,OFFSET PARAMETERS ;в BX - смещение ;---сохранить копии SS и SP MOV KEEP_SS,SS ;сохраняем SS MOV KEEP_SP,SP ;сохраняем SP ;---указываем на строку имени файла MOV DX,OFFSET FILENAME ;смещение - в DX MOV DS,AX ; ;---загрузка программы MOV AH,4BH ;функция EXEC MOV AL,0 ;выбираем "загрузку и запуск" INT 21H ;запускаем задачу ;---впоследствии, восстанавливаем регистры MOV SS,KEEP_SS ;восстанавливаем SS MOV SP,KEEP_SP ;восстанавливаем SP pop ds pop es popa iret Main endp init proc ;---замена прерывания--------------------------------- mov ah,25h mov al,4ah lea dx,Entry int 21h ;---сбрасываем будильник------------------------------ mov ah,07h int 1ah ;---устанавливаем будильник-------]-------------------- mov ah,06h mov ch,hours mov cl,minutes mov dh,seconds int 1ah ;---выгружаемся---------------------------------------- mov ax,3100h mov dx,(Init-Main+100h+0fh)/16 mov Size,dx int 21h init endp Code ends end Main Может я что то не так делаю? Может сегменты не туда настроены? А памяти ведь достаточно? В смысле
Минуточку, а это что? Код (Text): PARAMETERS DW 7 DUP(0) ;нулевой блок параметров ... ... ;---указываем на блок параметров MOV AX,DS ;в ES - сегмент MOV ES,AX ; MOV BX,OFFSET PARAMETERS ;в BX - смещение Я не могу понять почему при запуске из TS все путем?
Пардон, не заметил. Меня ещё смутило отсутствие определения сегмента кода Во-первых проверяй таки занятость DOS Во-вторых проверяй ошибку после вызова функции. Мне например сказали "Insufficient memory." Пробовал запускать программу не из обработчика прерывания? И проверять работу обработчика.
Как проверить занятость DOS? Ту прогу которую должОн запускать мой программ, я проверял - работает. Обработчик работает, если добавить выделение памяти (4ah). Я так понимаю после Код (Text): mov ax,3100h mov dx,(Init-Main+100h+0fh)/16 mov Size,dx int 21h Память выделяется? Как посмотреть ошибку вызова ф-ии? Я ведь не смогу не вывести на экран, ни дебагером перехватить.
Не понял про выделение памяти (4ah) После функции запуска поставь jc error - как и во многих других функциях DOS. Код ошибки будет в AX. Зачем переменная size? Прочитай сообщения 3 и 7 и скачай себе Ralph Brown interrupt list - нужная вещь, там всё написано.
Для запуска ещё одной проги нужна память. Оставаясь резидентными мы выделяем память. А для проверки работоспособности я просто выделил память ф-ией 4ah, а потом вызвал её. Это .com - Turbo Debugger не хочет видеть листинг, а без него плохо. ЭТО УЖАС! Как вообще в таком объёме инфы можно орентироваться в обычном FAR'e? Короче я не смог там найти int 28h. Гораздо удобнее на http://www.codenet.ru/progr/dos/, правда я так и не понял как ей пользоваться (в смысле int 28h).
Функция запуска сама выделяет память У меня всё нормально работает, часто пользуюсь TD. Я нормально ориентируюсь, правда в DN'е. Просто используй поиск по файлу. Кривовато :-(
Ничего она не выделяет, если выделять нечего. А выделять не будет чего, если вся память нашей прогой занята (дефаулт). Я не могу посмотреть код ошибки, потому что в момент запуска другой проги NTVDM виснет намертво.
Ну не вся память прогой занята, а только один сегмент. NTVDM у меня тоже падает (при сжатии области памяти), а в DOS всё работает.
Моя прога работает? Правда? ::какой-то радостный смайлик:: Пять минут спустя: А так ты об падении NTVDM. Не, у меня при сжатии памяти ничё не падает.