Автор: Пользователь скрыл имя, 10 Марта 2013 в 15:44, курс лекций
Один из основных принципов машины фон Неймана — то, что и программы, и данные хранятся в одной и той же памяти. Сохраняемая в памяти программа представляет собой некоторые коды, которые могут рассматриваться как данные. Возможно, с точки зрения программиста программа — активный компонент, она выполняет некоторые действия. Но с точки зрения процессора команды программы — это данные, которые процессор читает и интерпретирует. С другой стороны программа — это данные с точки зрения обслуживающих программ, например, с точки зрения компилятора, который на входе получает одни данные — программу на языке высокого уровня (ЯВУ), а на выходе выдает другие данные — программу в машинных кодах.
1) указать Ассемблеру,
какие cегментные регистры
2) сохранить в стеке адрес, находящийся в регистре DS, когда программа начнет выполнение;
3) записать в стек нулевой адрес;
4) загрузить в регистр DS адрес сегмента данных.
Выход из программы и возврат в DOS сводится к использованию команды RET.
Ассоциируя сегменты с сегментными регистрами, Ассемблер сможет определить смещения к отдельным областям в каждом сегменте. Например, каждая команда в сегменте кодов имеет определенную длину: первая команда имеет смещение 0, и если это двухбайтовая команда, то вторая команда будет иметь смещение 2 и так далее.
Загрузочному модулю в памяти непосредственно предшествует 256-байтовая (шест.100) область, называемая префиксом программного сегмента PSP. Программа загрузчика использует регистр DS для установки адреса начальной точки PSP. Пользовательская программа должна сохранить этот адрес, поместив его в стек. Позже, команда RET использует этот адрес для возврата в DOS.
В системе требуется, чтобы следующее значение в стеке являлось нулевым адресом (точнее, смещением). Для этого команда SUB очищает регистр AX, вычитая его из этого же регистра AX, а команда PUSH заносит это значение в стек.
Загрузчик DOS устанавливает правильные адреса стека в регистре SS и сегмента кодов в регистре CS. Поскольку программа загрузчика использует регистр DS для других целей, необходимо инициализировать регистр DS двумя командами MOV.
Команда RET обеспечивает выход из пользовательской программы и возврат в DOS, используя для этого адрес, записанный в стек в начале программы командой PUSH DS. Другим обычно используемым выходом является команда INT 20H.
Системный загрузчик при загрузке программы с диска в память для выполнения устанавливает действительные адреса в регистрах SS и CS. Программа не имеет сегмента данных, так как в ней нет определения данных и, соответственно, в ASSUME нет необходимости ассигновать pегистр DS.
Команды PUSH, SUB и
PUSH выполняют стандартные действия
для инициализации стека
Важно:
u Не забывайте ставить символ «точка с запятой» перед комментариями.
u Завершайте каждый сегмент директивой ENDS, каждую процедуру — директивой ENDP, а программу — директивой END.
u В директиве ASSUME устанавливайте соответствия между сегментными регистрами и именами сегментов.
u Для EXE-программ обеспечивайте не менее 32 слов для стека, соблюдайте соглашения по инициализации стека командами PUSH, SUB и PUSH и заносите в регистр DS адрес сегмента данных.
Лекция 9.
Ввод и выполнение программ
4
Ввод программы
Исходный текст программы, предназначенный для ввода с помощью текстового редактора можно ввести при помощи DOS EDLIN или другого текстового редактора. Для ввода исходной программы наберите команду:
EDLIN имя программы.ASM [Enter]
В результате DOS загрузит EDLIN в памяти и появится сообщение «New file» и приглашение «*-». Введите команду I для ввода строк, и затем наберите каждую ассемблерную команду.
Хотя число пробелов в тексте для Ассемблера не существенно, старайтесь записывать метки, команды, операнды и комментарии, выровненными в колонки, программа будет более yдобочитаемая. Для этого в EDLIN используется табуляция через каждые восемь позиций.
После ввода
программы убедитесь в ее правильности.
Затем наберите E (и Enter) для завершения
EDLIN. Можно проверить наличие
DIR (для всех файлов)
или
DIR имя программы.ASM (для одного файла)
В случае, если предполагается
ввод исходного текста большего объема,
то лучшим применением будет
PRINT имя программы.ASM [Enter]
Программа еще не может быть выполнена — прежде необходимо провести ее ассемблирование и компоновку.
4
Подготовка программы для
После ввода на диск исходной программы необходимо проделать два основных шага, прежде чем программу можно будет выполнить. Сначала необходимо ассемблиpовать программу, а затем выполнить компоновку. Программисты на языке бейсик могут выполнить программу сразу после ввода исходного текста, в то время как для Ассемблера и компилярных языков нужны шаги трансляции и компоновки.
Шаг ассемблирования
включает в себя трансляцию исходного
кода в машинный объектный код
и генерацию OBJ-модуля. OBJ-модуль уже
более приближен к
Шаг компоновки включает преобразование OBJ-модуля в EXE (исполнимый) модуль, содержащий машинный код. Программа LINK, находящаяся на диске DOS, выполняет следующее:
1. Завершает
формирование в OBJ-модуле
2. Компонует, если необходимо,
более одного отдельно
3. Инициализирует EXE-модуль
командами загрузки для
После компоновки OBJ-модуля (одного или более) в EXE-модуль, можно выполнить EXE-модуль любое число раз. Но, если необходимо внести некоторые изменения в EXE-модуль, следует скорректировать исходную программу, ассемблировать ее в другой OBJ-модуль и выполнить компоновку OBJ-модуля в новый EXE-модуль. Даже, если эти шаги пока остаются непонятными, вы обнаружите, что, получив немного навыка, весь процесс подготовки EXE-модуля будет доведен до автоматизма. Заметьте: определенные типы EXE-программ можно преобразовать в очень эффективные COM-программы.
4
Ассемблирование программы
Для того, чтобы выполнить исходную ассемблерную программу, необходимо прежде провести ее ассемблирование и затем компоновку. На дискете с ассемблерным пакетом имеются две версии aссемблера. ASM.EXE — сокращенная версия с отсутствием некоторых незначительных возможностей и MASM.EXE — полная версия. В случае, если размеры памяти позволяют, то используйте версию MASM.
Простейший вариант вызова программы ассемблирования — это ввод команды MASM (или ASM), что приведет к загрузке программы Ассемблера с диска в память. На экране появится:
source filename [.ASM]:
object filename [filename.OBJ]:
source listing [NUL.LST]:
cross-reference [NUL.CRF]:
Курсор при этом расположится в конце первой строки, где необходимо указать имя файла. Не следует набирать тип файла ASM, так как Ассемблер подразумевает это.
Во-втором запросе предполагается аналогичное имя файла (но можно его заменить).
Третий запрос предполагает, что листинг ассемблирования программы не требуется.
Последний запрос предполагает, что листинг перекрестных cсылок не требуется.
В случае, если вы хотите оставить значения по умолчанию, то в трех последних запросах просто нажмите Enter.
Всегда необходимо вводить имя исходного файла и, обычно, запрашивать OBJ-файл — это требуется для компоновки программы в загрузочный файл.
Возможно потребуется
указание LST-файла, особенно, если необходимо
проверить сгенерированный
Ассемблер преобразует исходные команды в машинный код и выдает на экран сообщения о возможных ошибках. Типичными ошибками являются нарушения ассемблерных соглашений по именам, неправильное написание команд (например, MOVE вместо MOV), а также наличие в опеpандах неопределенных имен. Программа ASM выдает только коды ошибок, которые объяснены в руководстве по Ассемблеру, в то время как программа MASM выдает и коды ошибок, и пояснения к ним. Всего имеется около 100 сообщений об ошибках.
Ассемблер делает
попытки скорректировать
Листинг содержит не только исходный текст, но также слева транслированный машинный код в шестнадцатеричном формате. В самой левой колонке находится шест.адреса команд и данных.
За листингом
ассемблирования программы
Вторая часть содержит идентификаторы — имена полей данных в сегменте данных и метки, назначенные командам в сегменте кодов. Для того, чтобы Ассемблер не создавал эту таблицу, следует указать параметр /N вслед за командой MASM, то есть:
MASM/N
Двухпроходный Ассемблер
В процессе трансляции
исходной программы Ассемблер делает
два просмотра исходного
В первом проходе Ассемблер просматривает всю исходную прогpамму и строит таблицу идентификаторов, используемых в программе, то есть, имен полей данных и меток программы и их относительных aдресов в программе. В первом проходе подчитывается объем объектного кода, но сам объектный код не генерируется.
Во втором проходе Ассемблер использует таблицу идентификаторов, построенную в первом проходе. Так как теперь уже известны длины и относительные адреса всех полей данных и команд, то Ассемблер может сгенерировать объектный код для каждой команды. Ассемблер создает, если требуется, файлы: OBJ, LST и CRF.
4
Компоновка программы
В случае, если в результате ассемблирования не обнаружено ошибок, то cледующий шаг — компоновка объектного модуля. Файл имяпрограммы.OBJ содержит только машинный код в шестнадцатеричной форме. Так как программа может загружаться почти в любое место памяти для выполнения, то Ассемблер может не определить все машинные адреса. Кроме того, могут использоваться другие (под) программы для объединения с основной. Назначением программы LINK является завершение определения адресных ссылок и объединение (если требуется) нескольких программ.
Для компоновки ассемблированной программы введите команду LINK и нажмите клавишу Enter. После загрузки в память, компоновщик выдает несколько запросов (аналогично MASM), на которые необходимо ответить:
Object Modules [.OBJ]: имя программы
Компонует имя программы.OBJ
Run file [имя программы.EXE]:
Создает имя программы.EXE
List file [NUL.MAP]: CON
Создает имя программы.MAP
Libraries [.LIB]: [Enter]
По умолчанию
Первый запрос — запрос имен объектных модулей для компоновки, тип OBJ можно опустить.
Второй запрос — запрос имени исполнимого модуля (файла), (по умолчанию имя программы.EXE). Практика сохранения одного имени (при разных типах) файла упрощает работу с программами.
Третий запрос предполагает, что LINK выбирает значение по yмолчанию — NUL.MAP (то есть, MAP отсутствует). MAP-файл содержит таблицу имен и размеров сегментов и ошибки, которые обнаружит LINK. Типичной ошибкой является неправильное определение сегмента стека. Ответ CON предполагает, что таблица будет выведена на экран, вместо записи ее на диск. Это позволяет сэкономить место в дисковой памяти и сразу просмотреть таблицу непосредственно на экране.
Для ответа на четвертый запрос — нажмите Enter, что укажет компоновщику LINK принять остальные параметры по yмолчанию.
На данном этапе единственной возможной ошибкой может быть yказание неправильных имен файлов. Исправить это можно только перезапуском программы LINK.
4
Выполнение программы
После ассемблирования и компоновки программы можно (наконец-то!) выполнить ее. В случае, если EXE-файл находится на дисководе C, то выполнить ее можно командой:
C:имя программы.EXE или C:имя программы
DOS предполагает,
что файл имеет тип EXE (или
COM), и загружает файл для
DEBUG C:имя программы.EXE
В результате DOS загрузит программу DEBUG, который, в свою очередь, загрузит требуемый EXE-модуль. После этого отладчик выдаст дефис (-) в качестве приглашения. Для просмотра сегмента стека введите
D SS:0
Эту область легко узнать по 12-кратному дублированию константы STACKSEG. Для просмотра сегмента кода введите
D CS:0
Введите R для
просмотра содержимого
В процессе пошагового выполнения программы обратите внимание на содержимое регистров. Когда вы дойдете до команды RET, можно ввести Q (Quit — выход) для завершения работы отладчика.