Пау-чок
Вопрос для знатоков КР580ВМ80/i8080.
Предыстория:
Для отладки программы под КР580ВМ80 решил использовать эмулятор i8080 (сей). Но обнаружил, что им не интерпретируется команда DAA. Естественное решение - приписать обработчик команды самому, благо код эмулятора доступен.
И вот тут столкнулся с затруднением такого плана... Как написано здесь (.doс):
Команда десятичной коррекции аккумулятора DAA осуществляет перевод 8-разрядного двоичного числа в аккумуляторе в две цифры двоично-десятичного кода с правильной установкой признака переноса CY. При этом производятся следующие действия:
1. Если младшая тетрада содержит число, больше 910, или установлен признак вспомогательного переноса АС=1, то содержимое аккумулятора увеличивается на 6.
2. Если после этого старшая тетрада аккумулятора содержит число, большее 9, или установлен признак вспомогательного переноса CY=1, то в старшую тетраду прибавляется 6.
Так вот. Реализовалось вышенаписанное таким образом:
Здесь ADD() - макросс, реализующий ADD и ADI со всеми вытекающими для регистра флагов последствиями.
И всё бы хорошо, если бы после выполнения первого ADD'а не терялся бит CY. А он стопроцентно теряется. И таким образом, скажем, сложение 0x95h+0x79h (BCD-представления) будет производиться как:
0x95h+0x79=0x10E(CY=1;A=0x0E)->ADD[1]->(CY=0;AC=1;A=0x14),
что мягко говоря не верно. И соотетственно, ADD[2] не выполнится, т.к. первая тетрада A меньше девяти и CY=0.
Естественно, реализовать функцию DAA, чтобы она работала так как мне надо - проще простого.
Но тут встаёт (внимание!) вопрос - DAA работает в КР580ВМ80 так как надо мне, или так как у меня реализуется, т.е. с потерей CY при первом цикле сожения?
Предыстория:
Для отладки программы под КР580ВМ80 решил использовать эмулятор i8080 (сей). Но обнаружил, что им не интерпретируется команда DAA. Естественное решение - приписать обработчик команды самому, благо код эмулятора доступен.
И вот тут столкнулся с затруднением такого плана... Как написано здесь (.doс):
Команда десятичной коррекции аккумулятора DAA осуществляет перевод 8-разрядного двоичного числа в аккумуляторе в две цифры двоично-десятичного кода с правильной установкой признака переноса CY. При этом производятся следующие действия:
1. Если младшая тетрада содержит число, больше 910, или установлен признак вспомогательного переноса АС=1, то содержимое аккумулятора увеличивается на 6.
2. Если после этого старшая тетрада аккумулятора содержит число, большее 9, или установлен признак вспомогательного переноса CY=1, то в старшую тетраду прибавляется 6.
Так вот. Реализовалось вышенаписанное таким образом:
if (( (A & 0x0F) > 0x09 ) || ( F & FLAG_AC ))
ADD(0x06); //[1]
if (( (A & 0xF0) > 0x90) || ( F & FLAG_C ))
ADD(0x60); //[2]
Здесь ADD() - макросс, реализующий ADD и ADI со всеми вытекающими для регистра флагов последствиями.
И всё бы хорошо, если бы после выполнения первого ADD'а не терялся бит CY. А он стопроцентно теряется. И таким образом, скажем, сложение 0x95h+0x79h (BCD-представления) будет производиться как:
0x95h+0x79=0x10E(CY=1;A=0x0E)->ADD[1]->(CY=0;AC=1;A=0x14),
что мягко говоря не верно. И соотетственно, ADD[2] не выполнится, т.к. первая тетрада A меньше девяти и CY=0.
Естественно, реализовать функцию DAA, чтобы она работала так как мне надо - проще простого.
Но тут встаёт (внимание!) вопрос - DAA работает в КР580ВМ80 так как надо мне, или так как у меня реализуется, т.е. с потерей CY при первом цикле сожения?
По идее, во всех процах, начиная с 8080 они работают одинаково. Во всяком случае, так считает Борданд =)
По идее, во всех процах, начиная с 8080 они работают одинаково
Может быть и так... Вот только 8080 имеет абсолютно дргие коды комманд, так что может быть это и не так...
Всё же посмотрю, как именно работает. Спасибо.
if AF=1 then AL:=AL+0110b
else if AL>1001b then AL:=AL-1010b; AH:=AH+1
if CF=1 then AH:=AH+0110b
else if AH>1001b then AH:=AH-1010b; CF:=1
Взято с http://hscool.net/online/base1_8.html
Буду надеяться, и 8080 работает так же... Хотя... Ну что за проклятие, тут не устанавливается AF...