|
В группе команд пересылки данных
сопроцессора 8087 имеется
всего три основных команды. Команда загрузки помещает данные в
регистровый стек 8087. Обычно эти данные читаются из памяти
системы, но команда загрузки может также
извлечь число из самого
стека и заменить им вершину стека. Команда записи берет данные из
вершины стека и помещает их в память
ЭВМ. Команда замены
обменивает два числа в регистровом стеке
сопроцессора 8087.
На Фиг. 7.10 показан листинг ассемблера
команд пересылки
данных.
В текст в самом начале помещен набор макрокоманд
процессора 8087 с помощью фрагмента:
IF1
INCLUDE
87MAC.LIB
ENDIF
Эта последовательность команд помещает в
текст программы
макрокоманды определения команд
сопроцессора 8087 во время первого
прохода ассемблера, когда должны
обрабатываться макрорасширения.
Ассемблер не читает файл макрокоманд во
время второго прохода, так
как этот файл больше не нужен. В листинге ассемблера появляется
только команда ENDIF.
Первая команда пересылки данных, которую
мы рассмотрим -
команда загрузки. Название всех команд сопроцессора 8087
начинается с буквы "F". Так что, чтобы загрузить число в
микросхему 8087, используется команда FLD
(Floating LoaD, плавающая
загрузка). В
отличие от команд микропроцессора 8088, где команда
MOV обслуживает все форматы данных, здесь
существует разная
Microsoft (R) Macro Assembler Version
5.00 1/1/80 01:21:45
Фиг. 7.10 Команды пересылки сопроцессора 8087 Page 1-1
PAGE
,132
TITLE
Фиг. 7.10 Команды пересылки сопроцессора 8087
0000 CODE
SEGMENT
ASSUME
CS:CODE,DS:CODE
0000 WORD_INTEGER LABEL WORD
0000 SHORT_INTEGER LABEL DWORD
0000 LONG_INTEGER LABEL QWORD
0000 BCD_INTEGER LABEL TBYTE
0000 SHORT_REAL LABEL DWORD
0000 LONG_REAL LABEL QWORD
0000 TEMPORARY_REAL LABEL
TBYTE
0000 9B DF 06 0000 R FILD
WORD_INTEGER
0005 9B DB 06 0000 R FILD
SHORT_INTEGER
000A 9B DF 2E 0000 R FILD
LONG_INTEGER
000F 9B DF 26 0000 R FBLD
BCD_INTEGER
0014 9B D9 06 0000 R FLD
SHORT_REAL
0019 9B DD 06 0000 R FLD
LONG_REAL
001E 9B DB 2E 0000 R FLD
TEMPORARY_REAL
0023 9B D9 C2 FLD
ST(2)
0026 9B DF 16 0000 R FIST
WORD_INTEGER
002B 9B DB 16 0000 R FIST
SHORT_INTEGER
0030 9B D9 16 0000 R FST
SHORT_REAL
0035 9B DD 16 0000 R FST
LONG_REAL
003A 9B DD D2 FST
ST(2)
003D 9B DF 1E 0000 R FISTP
WORD_INTEGER
0042 9B DB 1E 0000 R FISTP
SHORT_INTEGER
0047 9B DF 3E 0000 R FISTP
LONG_INTEGER
004C 9B DF 36 0000 R FBSTP
BCD_INTEGER
0051 9B D9 1E 0000 R FSTP
SHORT_REAL
0056 9B DD 1E 0000 R FSTP
LONG_REAL
005B 9B DB 3E 0000 R FSTP
TEMPORARY_REAL
0060 9B DD DA FSTP
ST(2)
0063 9B D9 CA FXCH
ST(2)
0066 9B D9 EE FLDZ
0069 9B D9 E8 FLD1
006C 9B D9 EB FLDPI
006F 9B D9 E9 FLDL2T
0072 9B D9 EA FLDL2E
0075 9B D9 EC FLDLG2
0078 9B D9 ED FLDLN2
007B CODE
ENDS
END
Фиг. 7.10 Команды пересылки сопроцессора 8087
мнемоника для разных типов данных. Так получилось потому, что
ассемблер может различать четырехбайтовые
и восьмибайтовые
операнды, но не может знать, является ли
операнд действительным или
целым числом.
Всякий раз, когда операнд - целое,
используется команда FILD.
Итак, FILD загружает слово (16 бит),
короткое целое число (32 бита)
или длинное целое число (64 бита). Чтобы загрузить упакованное
десятичное число (80 бит), используется
команда FBLD. Буква B
указывает десятичные числа. Наконец, команда FLD загружает
действительные числа. Ассемблер определяет, какой вид целого или
действительного числа вы желаете
использовать.
В ассемблере для имен команд сопроцессора
8087, ссылающихся к
памяти, используется соглашение о том, что
в случае целых чисел
вслед за буквой F следует буква I, в
случае десятичных чисел -
буква B, и никакой буквы не следует в
случае действительных чисел.
Мы увидим, что то же соглашение
используется и в командах записи, и
в арифметических командах, которые
указывают операнд в памяти.
Как видно из Фиг. 7.10, для каждого из
семи обслуживаемых
сопроцессором 8087 типов данных существует
команда загрузки.
Команда загрузки указывает поле данных в
памяти, микросхема 8087
преобразует данные из их внешнего
представления во временный
действительный формат. Преобразованное число помещается в стек,
увеличивая его объем на единицу. Если вы попытаетесь поместить
число в стек, который уже содержит восемь
чисел, сопроцессор 8087
сообщит об особой ситуации - переполнении
стека. Если программа не
обрабатывает особую ситуацию в своей
собственной подпрограмме,
встроенный обработчик особой ситуации
пометит загруженное значение,
как "неопределенное". Это означает, что дальнейшие действия с этим
числом дадут неопределенные
результаты. Если вы сделаете ошибку,
сопроцессор 8087 проследит за тем, чтобы
она не осталась
незамеченной.
Оставшаяся разновидность команды загрузки
берет один из
элементов стека и помещает его в
стек. Например, команда
FLD
ST0
дублирует вершину стека. После нее два верхних элемента имеют
одинаковые значения. Команда
FLD
ST3
помещает копию четвертого элемента стека в
стек. Заметим, что
число, которое было раньше ST3, стало
теперь ST4.
Давайте посмотрим на машинный язык, в
действительности
формируемый этими командами. Поскольку этот текст порождает
команды процессора 8087 с помощью
макрокоманд, сравнительно легко
увидеть, откуда появляются различные части
команд. Во=первых,
каждая команда начинается с байта
09BH. Это - команда WAIT. Как
вы помните, сопроцессор 8087 должен быть
синхронизирован с работой
микропроцессора 8088. Если микропроцессор 8088 попытается
выполнить следующую команду сопроцессора
8087 до того, как
сопроцессор 8087 завершит текущую команду,
действия микросхемы 8087
дадут неверный результат. Фактически все макрокоманды 8087
содержат команду WAIT для обеспечения
синхронизации. (Команды без
синхронизации сопроцессора 8087 - это все
команды управления,
обычно не требеющие ожидания
результата. Эти команды можно легко
отличить так как они все начинаются с FN, где
буква N означает
отсутствие синхронизации).
По макрорасширениям также можно видеть,
что команды процессора
8087 формируются командами ESC. Чтобы указать адрес памяти,
команда ESC имеет два операнда. Первый определяет, какая это
команда ESC, а второй ссылается на ячейку
памяти. Команда ESC
может иметь длину два, три или четыре
байта, в зависимости от
размера поля индексного смещения,
сопровождающего байт mod=r/m. В
комбинации с командой WAIT максимальная
длина команды сопроцессора
8087 достигает пяти байт.
Команда записи имеет два варианта. Первый вариант этой команды
извлекает число с вершины стека и
записывает ее в поименованную
ячейку памяти. Выполняя эту команду, сопроцессор 8087 делает
преобразование данных из временного
действительного формата в
желаемую внешнюю форму. Эта команда имеет коды операций FST и
FIST.
(Заметим, что здесь продолжают свое действие соглашения об
именах команд). Этой же командой вы можете занести вершину стека в
любое место внутри стека.
Вероятно вы заметили, что команда FST не
допускает запись всех
возможных внешних типов данных. Допустимы лишь типы из "большой
четверки" - целое слово, короткое
целое, короткое и длинное
действительные. Эта команда не поддерживает все внешниие типы
данных, потому что создатели процессора
8087 понимали, что это не
обязательно из=за свойств следующей
команды.
Второй вариант команды записи, кроме
записи данных, также
изменяет положение указателя стека. Команды FSTP (а также команды
FISTP и FBSTP) выполняют ту же операцию
записи данных из
сопроцессора 8087 в память, но они также
извлекают число из стека.
Эта разновидность команд поддерживает все
внешние типы данных.
Конструкторы микросхемы 8087 кое=где
экономили на командах, и
поэтому только команды FLD и FSTP
поддерживают все внешние типы
данных.
Все остальные команды сохранения данных в памяти работают
только с "большой четверкой" типов
данных. Конструкторы понимали,
что эти четыре типа будут преобладать над
всеми, и использование
других форматов может быть реализовано
только командами FLD и FSTP.
Команда замены FXCH - следующая команда в
группе команд
пересылки данных. Команда FXCH меняет местами содержимое
вершины
стека с содержимым другого регистра стека. Эта команда может
использовать в качестве операнда только
другой элемент стека.
Нельзя одной командой поменять местами
содержимое вершины стека и
ячейки памяти. Эта процедура потребует несколько команд и рабочее
поле где=то в памяти. В отличие от микропроцесоора 8088,
сопроцессор 8087 может в одной команде
выполнить чтение из памяти
или запись в память, но не то или другое
одновременно.
Команда Константа
--------------------------
FLDZ 0
FLD1 1
FLDPI PI
FLDL2T LOG2(10)
FLDL2E LOG2(e)
FLDG2 LOG10(2)
FLDLN2 LOGe(2)
-------------------------- Фиг. 7.11
Константы 8087
Остальные команды группы команд персылки
данных обслуживают
константы. Они
загружают в стек заранее известные значения.
Эти
константы описывают набор величин,
необходимых программам при
вычислениях, и были выбраны из соображений
упрощения счета
трансцендентных и тригонометрических
функций. Мы используем
некоторые из этих констант в
демонстрационных программах. Таблица
на Фиг. 7.11 показывает, какое именно
значение загружается в элемент
ST0
в случае каждой команды. В каждом
случае мнемоника команды
выбрана так, чтобы отражать значение
константы.
Microsoft (R) Macro Assembler Version 5.00 1/1/80 04:04:07
Фиг. 7.12 Команды управления сопроцессора 8087 Page 1-1
PAGE
,132
TITLE
Фиг. 7.12 Команды управления сопроцессора 8087
0000 CODE
SEGMENT
ASSUME
CS:CODE
0000 STATUS_WORD LABEL WORD
0000 CONTROL_WORD LABEL WORD
0000 ENVIRONMENT LABEL BYTE ;
Область размером 14 байт
0000 STATE LABEL
BYTE ; Область размером 94 байта
0000 9B DB E3 FINIT
0003 9B DB E0 FENI
0006 9B DB E1 FDISI
0009 9B 2E: D9 2E 0000 R FLDCW
CONTROL_WORD
000F 9B 2E: D9 3E 0000 R FSTCW
CONTROL_WORD
0015 9B DB E2 FCLEX
0018 9B 2E: D9 36 0000 R FSTENV
ENVIRONMENT
001E 9B 2E: D9 26 0000 R FLDENV
ENVIRONMENT
0024 9B 2E: DD 36 0000 R FSAVE
STATE
002A 9B 2E: DD 26 0000 R FRSTOR
STATE
0030 9B D9 F7 FINCSTP
0033 9B D9 F6 FDECSTP
0036 9B DD C2 FFREE
ST(2)
0039 9B D9 D0 FNOP
003C 9B FWAIT
003D CODE
ENDS
END
Фиг. 7.12 Команды управления сопроцессора 8087
| |