Zilog Z80/Система команд/INI
Этот документ создан для Emuverse и распространяется на условиях лицензии CC-BY-SA-3.0. |
Найденная в Интернете информация сильно отличается от официальных данных (особенно, в отношении флагов N и CY). Все сказанное ниже относится к блочным командам ввода-вывода INI/INIR/OUTI/OTIR и IND/INDR/OUTD/OTDR.
Флаги устанавливаются следующим образом:
- S, Z, F5, F3 из декремента B (официально — S неизвестен; информация по Z совпадает);
- N — копия 7-го бита значения, полученного/переданного в порт (по официальным данным равен 1);
Далее для получения CY (официально — не меняется) и HC (официально — неизвестен):
- Прибавить к значению регистра C единицу, если инструкция увеличивала HL, иначе отнять единицу;
- Добавить к этому значению байт, полученный или переданный в порт;
- Скопировать признак переноса этой операции во флаги CY и HY (то есть они будут одинаковые).
PV (официально — неизвестен) зависит от значения регистров B, C и переданного байта (по информации Pedro Gimeno (pgimeno@geocities.com)):
- Для INI/INIR/OUTI/OTIR
1. Вычисление первой промежуточной переменной Temp1(С.1 обозначает 1-й бит регистра и т. д., inp — переданный байт):
C.1 | C.0 | inp.1 | inp.0 | Temp1 |
---|---|---|---|---|
0 | 0 | 0 | 0 | 0 |
0 | 0 | 0 | 1 | 0 |
0 | 0 | 1 | 0 | 1 |
0 | 0 | 1 | 1 | 0 |
0 | 1 | 0 | 0 | 0 |
0 | 1 | 0 | 1 | 1 |
0 | 1 | 1 | 0 | 0 |
0 | 1 | 1 | 1 | 1 |
1 | 0 | 0 | 0 | 1 |
1 | 0 | 0 | 1 | 0 |
1 | 0 | 1 | 0 | 1 |
1 | 0 | 1 | 1 | 1 |
1 | 1 | 0 | 0 | 0 |
1 | 1 | 0 | 1 | 1 |
1 | 1 | 1 | 0 | 1 |
1 | 1 | 1 | 1 | 0 |
2. Вычисление второй промежуточной переменной:
Если (B AND 0xF = 0) то Temp2 = Parity(B) XOR (B.4 OR (B.6 AND NOT B.5)) иначе Temp2 = Parity(B) XOR (B.0 OR (B.2 AND NOT B.1))
где Parity - обычная операция вычисления четности
Реально данную операцию проще выполнять по таблице:
0123456789ABCDEF <- (нижний полубайт B) 00 0011010011001011 10 0100101100110100 20 1100101100110100 30 1011010011001011 40 0100101100110100 50 1011010011001011 60 0011010011001011 70 0100101100110100 80 1100101100110100 90 1011010011001011 A0 0011010011001011 B0 0100101100110100 C0 1011010011001011 D0 0100101100110100 E0 1100101100110100 F0 1011010011001011 ^ (Верхний полубайт B)
Тогда PV = Temp1 XOR Temp2 XOR C.2 XOR inp.2
- IND/INDR/OUTD/OTDR
Аналогично INI, только отличается первая таблица:
C.1 | C.0 | inp.1 | inp.0 | Temp1 |
---|---|---|---|---|
0 | 0 | 0 | 0 | 0 |
0 | 0 | 0 | 1 | 1 |
0 | 0 | 1 | 0 | 0 |
0 | 0 | 1 | 1 | 0 |
0 | 1 | 0 | 0 | 1 |
0 | 1 | 0 | 1 | 0 |
0 | 1 | 1 | 0 | 0 |
0 | 1 | 1 | 1 | 1 |
1 | 0 | 0 | 0 | 0 |
1 | 0 | 0 | 1 | 0 |
1 | 0 | 1 | 0 | 1 |
1 | 0 | 1 | 1 | 0 |
1 | 1 | 0 | 0 | 0 |
1 | 1 | 0 | 1 | 1 |
1 | 1 | 1 | 0 | 0 |
1 | 1 | 1 | 1 | 1 |