Набросок РЛК на собственном процессоре.

Советский компьютер Радио-86РК (1986) и его клоны

Moderator: Shaos

User avatar
Paguo-86PK
Maniac
Posts: 267
Joined: 12 Apr 2011 20:43
Location: Tashkent

Набросок РЛК на собственном процессоре.

Post by Paguo-86PK »

С самого детства, с тех пор, как я познакомился с РК, у меня родилась мечта сделать свою ЭВМ.
Прошло очень много лет. То ли из-за нехватки отладочной платы с ПЛИС, то ли по каким-то другим причинам. Но, мечта остаётся мечтою. Даже эмулятора нет...
Именно "РАДИО-86РК" интересен тем, что, отлично от "Специалиста" или "Ориона-128", в нём нет графической памяти. А значит, вся память может использоваться под нужды пользователя в рамках одной страницы.
К тому же, К580ВМ80А позволяет организовать т.н. Гарвардскую архитектуру: Разделить стек, данные и код на три независимые страницы. На сколько я понял из справочников, процессор периодически в шину данных посылает слово статуса: Цикл M1; Чтение/запись данных; Обращение к стеку. Тем самым, это уже не 64кб, а 192кб памяти, без всяких переключений страниц.

После сброса, к шине процессора подключается К155РЕ3 до тех пор, пока в цикле M1 не произойдёт чтение команды из старшей половины памяти:

Code: Select all

0000..7FFF M1 - ROM-К155РЕ3
0000..FFFF WR - RAM-64K
В этом режиме 32 байта кода ПЗУ должны загрузить BIOS в ОЗУ, а затем передать туда управление. Код примерно такой:

Code: Select all

0000: 21 00 E0 | MOV  BX,0xE000 ; Адрес внешнего ПЗУ
0003: F9       | MOV  SP,BX     ; Стек будет источником файла BIOS
0004: D1       | POP  DX        ; Читаем слово из ПЗУ
0005: 73 23    | MOVS [BX],DL   ; Записываем его по тому адресу,
0007: 72 23    | MOVS [BX],DH   ; но в память ОЗУ
0009: 7C       | MOV  AL,BH     ; Проверим, не вышел ли указатель
000A: 87       | ADD  AL,AL     ; за границы в 64Кб?
000B: DA 04 00 | JC  0x0004     ; Продолжаем заполнение памяти
000E: EB       | XCHG DX,BX     ; Последнее слово - адрес старта
000F: E9       | JMP  BX        ; Передаём управление "Монитору".
Активизация старшего бита адреса в цикле M1 отключает К155РЕ3 от шины до следующего сброса. Теперь пользователь имеет ровно 65536 байт ОЗУ.
Следует отметить, что стек здесь физически обеспечивает доступ к внешним устройствам (ВТ57, ВГ75, ВИ53, ВВ55). Так как прикладная программа не может постоянно менять режимы работы ВГ75 или ВИ53, доступ к ним через стек в этом случае достаточно оправдан.

Допустим, основная процедура инициализации дисплея теперь выглядит несколько громоздко и странно:

Code: Select all

FACE: E5 C5    | PUSH BX,CX     ; Сохраняем регистры
FAD0: 21 00 00 | MOV  BX,0x0000 ; Очищаем регистры
FAD3: 44 4D    | MOV  CX,BX
FAD5: 39       | ADD  BX,SP     ; Запоминаем указатель стека
FAD6: 31 12 C0 | MOV  SP,0xC012 ; ВГ75: Вместо C001 - C010
FAD9: C5       | PUSH CX        ; Записываем нули
FADA: 01 1D 4D | MOV  CX,0x4D1D ; Вместо C000 - C000..C00F
FADD: C5       | PUSH CX
FADE: 01 93 99 | MOV  CX,0x9993
FAE1: C5       | PUSH CX
FAE2: 31 12 C0 | MOV  SP,0xC012
FAE5: 01 27 27 | MOV  CX,0x2727
FAE8: C5       | PUSH CX
FAE9: F1       | POP  PSW
FAEA: 3B       | DEC  SP
FAEB: 3B       | DEC  SP
FAEC: E6 20    | AND  AL,0x20
FAEE: CA E9 FA | JZ   0xFAE9
FAF1: 31 12 E0 | MOV  SP,0xE012 ; То же самое с ВТ57
FAF4: 01 80 80 | MOV  CX,0x8080 ; Вместо E008 - E010
FAF7: C5       | PUSH CX
FAF8: 31 0A E0 | MOV  SP,0xE00A ; Вместо E004 - E008
FAFB: 01 76 D0 | MOV  CX,0xD076
FAFE: C5       | PUSH CX
FAFF: 31 0C E0 | MOV  SP,0xE00C ; Вместо E005 - E00A
FB02: 01 49 23 | MOV  CX,0x2349
FB05: C5       | PUSH CX
FB06: 31 12 E0 | MOV  SP,0xE012
FB09: 01 A4 A4 | MOV  CX,0xA4A4
FB0C: C5       | PUSH CX
FB0D: F9       | MOV  SP,BX
FB0E: C1 E1    | POP  CX,BX
FB10: C9       | RET
Тем не менее, я сторонник того, что редкие операции должны быть грубее частых.
Так, в архитектуре i8080 (Z80) мне не нравится следующее:
Команда 31 или F9 - указатель стека не так часто устанавливается. Можно было бы обойтись долгим циклом с 33 или 3B;
Команда E9 - можно было бы просто обойтись парой E5 C9.
(На эту тему я часто говорю на форумах относительно x86, где уйма мусорных AAA/AAD/AAM/AAS имеют по байту, а используются крайне редко.
У процессоров Intel это очень больная тема: Куча дурацких команд имеют компактные коды.


Таким образом, теоретически на ВМ80 (Z80) можно построить систему, где ОЗУ покрывает всё адресное пространство. А стек покрывает лишь младшую половину ОЗУ. Старшая предназначается под доступ к внешним устройствам.
Можно, конечно, возразить. Мол, опрос клавиатуры станет чудовищно сложным.
Ну я же не говорю о полной совместимости с РК. Опрос клавиатуры можно возложить на ПДП. Если её посадить на шину адреса (как в ZX) и считывать аппаратно состояние клавиш прямо в память.
Здесь, скажем, адреса матрицы клавиш будут 7F,BF,DF,EF,F7,FB,FD,FE в дампе из 256 байт.
Вот про ПДП

Также INT (RST) команды в данный момент прорабатываются. Так, RST 0 (C7) никогда не используется, так как стартует с 0000. Кажется, я нашёл способ обойти это препятствие:

Code: Select all

0000: F5       |PUSH PSW       ; Нужно убедиться, что это -
0001: E5       |PUSH BX        ; вызов RST 0, а не старт G0.
0002: 21 FF 89 |MOV  BX,0x89FF ; Проверяем по указателю стека.
0005: C3 _G0_  |JMP  _G0_
..............  ..............	
_G0_: 39       |ADD  BX,SP     ; Если стек уже иницирован этой
+001: E1       |POP  BX        ; данной программой, он будет
+002: D2 _C7_  |JNC  _C7_      ; меньше 0x7600
+005: 31 00 76 |MOV  SP,0x7600 ; Иначе, это старт - G0.
..............  ..............
_C7_: F1       |POP  PSW       ; Теперь, можно обрабатывать C7
+001: D2 11 +0 |JZ   +011      ; Если условие не выполняемо
+004: E3       |XCHG BX,[SP]   ; Извлекаем адрес возврата
+005: F5 C5    |PUSH PSW,CX    ; Сохраняем всё необходимое
+007: 4E       |MOV  CL,[BX]   ; Извлекаем байт смещения
+008: 79       |MOV  AL,CL     ; Здесь мы выполняем
+009: 87       |ADD  AL,AL     ; аналог
+00A: 9F       |SBB  AL,AL     ; x86-инструкции
+00B: 47       |MOV  CH,AL     ; MOVSX CX,CL
+00C: 09       |ADD  BX,CX     ; Смещаем IP на указанную
+00D: C1       |POP  CX        ; величину
+00E: 23       |INC  BX        ; Коррекция, т.к. прочли
+00F: E3       |XCHG BX,[SP]   ; относительный адрес
+010: C9       |RET            ; Получился аналог JR NZ (Z80)
+011: E3       |XCHG BX,[SP]   ; Условие не выполнилось
+012: F5       |PUSH PSW       ; Пропускаем байт относительного
+013: C3 0E +0 |JMP  +00E      ; перехода по условию
Теперь C7 - аналог JR NZ (20 ±127) процессора Z80. Медленный, но в нужных местах очень полезный!
Таким же образом реализуются JR Z, JR C и JR NC. Остальные RST выполняются в том же духе.
Например, BF F7 и 37 F7 - снимается/предустанавливается флаг CF, который можно использовать как переключатель. Скажем,
BF F7 - CALL 0xF812
37 F7 - CALL 0xF803
AF F7 - CALL 0xF81B
Целых три разных вызова...

M1 через ПЗУ:
Как-то была идея аппаратно пропускать байт инструкции через ПЗУ, где коды команд несколько упорядочить на свой лад:

 Таблица команд

Code: Select all

80x80  ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗   ╔═══╗
╔════╦═╝ x0╚═╤═╝ x1╚═╤═╝ x2╚═╤═╝ x3╚═╤═╝ x4╚═╤═╝ x5╚═╤═╝ x6╚═╤═╝ x7╚═╤═╝ x8╚═╤═╝ x9╚═╤═╝ xA╚═╤═╝ xB╚═╤═╝ xC╚═╤═╝ xD╚═╤═╝ xE╚═╤═╝ xF╚═╗
║ 0x ║PREFIX │MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║SS |HLT│BH,[BX]│CH,[BX]│DH,[BX]│AL,[BX]│BL,[BX]│CL,[BX]│DL,[BX]│AL,[BX]│AL,[BX]│AL,[BX]│AL,[BX]│AL,[BX]│AL,[BX]│AL,[BX]│AL,[BX]║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 1x ║MOV    │PREFIX │MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║[BX],BH│BH / BP│CH,BH  │DH,BH  │AL,BH  │BL,BH  │CL,BH  │DL,BH  │AL,BH  │AL,BH  │AL,BH  │AL,BH  │AL,BH  │AL,BH  │AL,BH  │AL,BH  ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 2x ║MOV    │MOV    │PREFIX │MOV    │MOV    │MOV    │MOV    │MOV    │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║[BX],CH│BH,CH  │CH / SI│DH,CH  │AL,CH  │BL,CH  │CL,CH  │DL,CH  │AL,CH  │AL,CH  │AL,CH  │AL,CH  │AL,CH  │AL,CH  │AL,CH  │AL,CH  ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 3x ║MOV    │MOV    │MOV    │PREFIX │MOV    │MOV    │MOV    │MOV    │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║[BX],DH│BH,DH  │CH,DH  │DH / DI│AL,DH  │BL,DH  │CL,DH  │DL,DH  │AL,DH  │AL,DH  │AL,DH  │AL,DH  │AL,DH  │AL,DH  │AL,DH  │AL,DH  ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 4x ║MOV    │MOV    │MOV    │MOV    │PREFIX │MOV    │MOV    │MOV    │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║[BX],AL│BH,AL  │CH,AL  │DH,AL  │AL / SP│BL,AL  │CL,AL  │DL,AL  │AL,AL  │AL,AL  │AL,AL  │AL,AL  │AL,AL  │AL,AL  │AL,AL  │AL,AL  ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 5x ║MOV    │MOV    │MOV    │MOV    │MOV    │PREFIX │MOV    │MOV    │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║[BX],BL│BH,BL  │CH,BL  │DH,BL  │AL,BL  │BL / BX│CL,BL  │DL,BL  │AL,BL  │AL,BL  │AL,BL  │AL,BL  │AL,BL  │AL,BL  │AL,BL  │AL,BL  ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 6x ║MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │PREFIX │MOV    │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║[BX],CL│BH,CL  │CH,CL  │DH,CL  │AL,CL  │BL,CL  │CL / CX│DL,CL  │AL,CL  │AL,CL  │AL,CL  │AL,CL  │AL,CL  │AL,CL  │AL,CL  │AL,CL  ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 7x ║MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │PREFIX │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║[BX],DL│BH,DL  │CH,DL  │DH,DL  │AL,DL  │BL,DL  │CL,DL  │DL / DX│AL,DL  │AL,DL  │AL,DL  │AL,DL  │AL,DL  │AL,DL  │AL,DL  │AL,DL  ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 8x ║NOP    │       │       │       │       │       │       │       │       │       │       │       │       │       │       │       ║
║    ║       │       │       │       │       │       │       │       │       │       │       │       │       │       │       │       ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ 9x ║CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   │CALL   ║
║    ║0xXX00 │0xXX10 │0xXX20 │0xXX30 │0xXX40 │0xXX50 │0xXX60 │0xXX70 │0xXX80 │0xXX90 │0xXXA0 │0xXXB0 │0xXXC0 │0xXXD0 │0xXXE0 │0xXXF0 ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ Ax ║MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │MOV    │ADC    │SBB    │ADD    │SUB    │AND    │OR     │XOR    │CMP    ║
║    ║[BX],IB│BH,IB  │CH,IB  │DH,IB  │AL,IB  │BL,IB  │CL,IB  │DL,IB  │AL,IB  │AL,IB  │AL,IB  │AL,IB  │AL,IB  │AL,IB  │AL,IB  │AL,IB  ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ Bx ║JZ     │JNZ    │JC     │JNC    │JPE    │JPO    │JS     │JNS    │CZ     │CNZ    │CC     │CNC    │CPE    │CPO    │CS     │CNS    ║
║    ║IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     │IB     ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ Cx ║INC    │INC    │INC    │INC    │INC    │INC    │INC    │INC    │INC    │INC    │INC    │INC    │CMC    │ROR    │RCL    │RCR    ║
║    ║[BX]   │BH     │CH     │DH     │AL     │BL     │CL     │DL     │SP     │BX     │CX     │DX     │       │AL     │AL     │AL     ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ Dx ║DEC    │DEC    │DEC    │DEC    │DEC    │DEC    │DEC    │DEC    │DEC    │DEC    │DEC    │DEC    │NOT    │       │RAL    │RAR    ║
║    ║[BX]   │BH     │CH     │DH     │AL     │BL     │CL     │DL     │SP     │BX     │CX     │DX     │AL     │       │AL     │AL     ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ Ex ║       │       │       │       │       │       │       │       │XCHG   │PUSH   │PUSH   │PUSH   │PUSH   │PUSH   │PUSH   │PUSH   ║
║    ║       │       │       │       │       │       │       │       │BX,[SP]│BX     │CX     │DX     │AX     │[BX]   │[IW]   │IW     ║
╟────╫───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────┼───────╢
║ Fx ║INT    │INT    │INT    │INT    │INT    │INT    │INT    │INT    │XCHG   │POP    │POP    │POP    │POP    │POP    │POP    │RET    ║
║    ║0      │1      │2      │3      │4      │5      │6      │7      │IP,[SP]│BX     │CX     │DX     │AX     │[BX]   │[IW]   │       ║
╚════╩═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╧═══════╝
77 44            |XCHG AL,DL
66 55            |XCHG BL,CL
55 66            |XCHG CX,BX
44 77            |XCHG DX,SP
55 73            |LEA  BX,[DH<<8+DL]
...
EE 34 12 FF      |JMP [0x1234]
EF 34 12 FF      |JMP  0x1234
EF 34 12 F8      |CALL 0x1234
EE 34 12 F9      |MOV BX,[0x1234]
E9 FE 34 12      |MOV [0x1234],BX
EF 34 12 E8 04 F9|MOV AL,[0x1234]|PUSH 0x1234+XCHG BX,[SP]+MOV AL,[BX]+POP BX
EF 34 12 E8 40 F9|MOV [0x1234],AL|PUSH 0x1234+XCHG BX,[SP]+MOV [BX],AL+POP BX
7F AC 3C         |AND DL,0x3C
66 83            |MOV [DX],CL
88 B2 FD         |CLC
88 B3 FD         |STC
B0 FE --         |REP Z
B0 FF --         |RET Z
B1 FE --         |REP NZ
B1 FF --         |RET NZ
B2 FE --         |REP C
B2 FF --         |RET C
B3 FE --         |REP NC
B3 FF --         |RET NC
B4 FE --         |REP PE
B4 FF --         |RET PE
B5 FE --         |REP PO
B5 FF --         |RET PO
B6 FE --         |REP S
B6 FF --         |RET S
B7 FE --         |REP NS
B7 FF --         |RET NS
B8 FE -<DEBUG#1>-|
B8 FF -<PROG#01>-|DAA
B9 FE -<DEBUG#2>-|
B9 FF -<PROG#02>-|DAS
BA FE -<DEBUG#3>-|
BA FF -<PROG#03>-|
BB FE -<DEBUG#4>-|
BB FF -<PROG#04>-|
BC FE -<DEBUG#5>-|
BC FF -<PROG#05>-|MUL
BD FE -<DEBUG#6>-|
BD FF -<PROG#06>-|DIV
BE FE -<DEBUG#7>-|
BE FF -<PROG#07>-|
BF FE -<DEBUG#8>-|
BF FF -<PROG#08>-|

При взломе программа будет выглядить неузнаваемо. Здесь я строил таблицу по принципам:
1. Код 00 в текстовых файлах, обычно, означает конец. А конец программы - HLT;
2. Код 80 - десятичное -128, которое не имеет отрицательного значения (-128 = NEG(-128)). Значит, пустая операция;
3. Холостые пересылки (MOV B,B/MOV C,C/MOV D,D и т.д.) работают как префикс подмены аккумулятора в вычислениях (mov b,b + ora a = orb a или mov d,d + cma = not d)
4. Команды из 2-х и 3-х байт сложены в стопку. Что упрощает дешифрацию (ассемблинг/дизассемблинг).

Так как я давно имею мечту разработать для ПЛИС свой вариант процессора на базе i8080, то систему команд можно переработать произвольно. А таблица - один из вариантов.
Last edited by Paguo-86PK on 02 Dec 2016 18:43, edited 9 times in total.
User avatar
Shaos
Admin
Posts: 24011
Joined: 08 Jan 2003 23:22
Location: Silicon Valley

Re: Набросок РК-несовместимой версии

Post by Shaos »

Так вроде вот тут мы выясняли, что аргументы многобайтовых команд тоже вычитывются как данные, т.е. по сути данные и команды в 8080 разделять нельзя...
Я тут за главного - если что шлите мыло на me собака shaos точка net
User avatar
Stan
Banned
Posts: 397
Joined: 04 Jan 2013 10:09
Location: 95.24.178.158

Re: Набросок РК-несовместимой версии

Post by Stan »

Paguo-86PK wrote:Именно "РАДИО-86РК" интересен тем, что, отлично от "Специалиста" или "Ориона-128", в нём нет графической памяти. А значит, вся память может использоваться под нужды пользователя в рамках одной страницы.
А чем мешает т.н. "графическая память" "Специалиста" или "Ориона-128" использованию всей памяти под нужды пользователя в рамках одной страницы?
У "Специалиста" и "Ориона-128" как раз реализована прозрачная регенерация ОЗУ и доступ к ОЗУ видеоподсистемы.
То есть, с точки зрения процессора ПК "Специалиста" и "Ориона-128" т.н. "графическая память" - это самая что ни на есть обычная память.
Процессору никак не заметно, что он обратился к "графической памяти" или к "НЕграфической памяти".

Т.е. в т.н. "графической памяти" процессор может выполнять программу, просто это будет отображаться на дисплее и не более того.
Вот типичный пример: адаптация к "Специалисту" игры ZX_Spectrum "Blob The Cop".
spblobcop.gif
Слева и справа от изображения поля игры мы видим программу, исполняемую в т.н. "графической памяти" .

Я думаю, что "РАДИО-86РК" в этом плане выглядит хуже: если Вы запретите вывод на символьный экран,
Вам придется регенерировать ОЗУ программным способом, поскольку в "РАДИО-86РК" циклы ПДП отвечают
как раз за регенерацию динамического ОЗУ.

Так что в плане использованию всей памяти под нужды пользователя в рамках одной страницы "Специалист" и "Ориона-128" пожалуй что предпочтительнее "РАДИО-86РК" будут!
Особенно "Орион-128" - у него область графического экрана расположена с адреса 0С000Н, т.е. в верхней четверти ОЗУ.
То есть нижние 48К полностью доступны пользователю, не залезая в область графического экрана.
А если использовать и область ОЗУ графического экрана, что никак не заметно процессору, то и в "Специалисте" и "Орионе-128" процесору доступны в качестве ОЗУ все 64КБайт - 2КБайт ПЗУ.
Но у "Специалиста_МХ" ситуация и еще лучше! В нем полностью доступны пользователю все 64КБайт ОЗУ - 32 Байта портов В/В.
You do not have the required permissions to view the files attached to this post.
User avatar
Paguo-86PK
Maniac
Posts: 267
Joined: 12 Apr 2011 20:43
Location: Tashkent

Re: Набросок РК-несовместимой версии

Post by Paguo-86PK »

Stan wrote:А чем мешает т.н. "графическая память" "Специалиста" или "Ориона-128" использованию всей памяти под нужды пользователя в рамках одной страницы?
У "Специалиста" и "Ориона-128" как раз реализована прозрачная регенерация ОЗУ и доступ к ОЗУ видеоподсистемы.
Хм, какрас прозрачная регенерация и помеха в подобных опытах.
User avatar
Stan
Banned
Posts: 397
Joined: 04 Jan 2013 10:09
Location: 95.24.178.158

Re: Набросок РК-несовместимой версии

Post by Stan »

Paguo-86PK wrote:
Stan wrote:А чем мешает т.н. "графическая память" "Специалиста" или "Ориона-128" использованию всей памяти под нужды пользователя в рамках одной страницы?
У "Специалиста" и "Ориона-128" как раз реализована прозрачная регенерация ОЗУ и доступ к ОЗУ видеоподсистемы.
Хм, какрас прозрачная регенерация и помеха в подобных опытах.
Аx, вон оно как...
подобные опыты wrote:Я вот о чём подумал.
Была у меня идейка...

Как известно, при отключении ПДП начинается разрушение данных в ОЗУ без регенерации. В каких-то - скорее, в каких-то - позднее. Уже в 2000-х, когда я нашёл в сети статьи про теорию торсионных полей, пробовал свой Пентиум превратить в датчик тупым отключением регенерации памяти. Пытался сначала общее ОЗУ разрушать. Не вышло. Потом видео пытался разрушать: Вычитал про бит порта видяхи, останавливающий вывод на экран с риском разрушения картинки. Но, как оказалось, то ли я некудышный до безобразия ламер, то ли технологии уже не поддавались деструктивному действию...
Только не надо тогда путать в одном посте "тёплое с мягким"... "какрас"...
"вся память может использоваться под нужды пользователя в рамках одной страницы" - это условно "тёплое",
а "статьи про теорию торсионных полей" - это, безусловно, "мягкое".

No comments...
viv-pm
Novelist
Posts: 31
Joined: 17 Mar 2015 21:54

Re: Набросок РК-несовместимой версии

Post by viv-pm »

Вообще-то, если слово состояния ВМ80 всё равно
дешифрируется, устройства целесообразно
разместить в адресном пространстве ввода-вывода,
а не стека, как собственно и сделано в большинстве
изделий на ВМ80.
Что касается выделения адресного пространства
команд - после дешифрирования цикла M1 дешифратор
может захватывать по сигналу RC код команды и при
наличии 2-х или 3-х байтовой команды следующие
1 или 2 цикла чтения памяти направлять в адресное
пространство команд (а не данных).
Дешифратор получается непростым, но вполне
реализуемым - одна РФ4 и несколько корпусов 1533.
User avatar
Paguo-86PK
Maniac
Posts: 267
Joined: 12 Apr 2011 20:43
Location: Tashkent

Re: Набросок РК-несовместимой версии

Post by Paguo-86PK »

viv-pm wrote:Вообще-то, если слово состояния ВМ80 всё равно
дешифрируется, устройства целесообразно
разместить в адресном пространстве ввода-вывода,
а не стека, как собственно и сделано в большинстве
изделий на ВМ80.
Что касается выделения адресного пространства
команд - после дешифрирования цикла M1 дешифратор
может захватывать по сигналу RC код команды и при
наличии 2-х или 3-х байтовой команды следующие
1 или 2 цикла чтения памяти направлять в адресное
пространство команд (а не данных).
Дешифратор получается непростым, но вполне
реализуемым - одна РФ4 и несколько корпусов 1533.
Есть другая идея. Сделать инструкции IN/OUT/DI/EI - привелегированными, как в защищённом режиме x86. Аппаратно сделать это легче лёгкого.
1. управление разрешением прерываний проецируется прямо в динамик.
Парные инструкции (1.DI+DI / 2.EI+DI / 3.DI+EI / 4.EI+EI) следующие друг за другом не влияют на бит звука, а переключают режим памяти, выбирают страницу (подобие LOCK). Бит накапливает в специальный сдвиговый регистр (можно набить и 7 - DI+EI+EI+EI+DI+DI+DI, и т.д.)
Так, EI+EI+MOV A,M -> загрузить байт из 4-й страницы памяти...
2. Команды IN/OUT оформить обращением к API-Монитора. Вместо 580ВН59 формировать нужную команду CALL, где имитировать доступ к портам:
Так, IN 3 -> CALL 0xF803 или OUT 9 -> CALL 0xF809...
Конечно, всё станет работать медленнее. Но, так можно достигнуть как в x86 виртуализацию. Убрать программу "Монитор" из адресного пространства вовсе. И включать код "Монитора" лишь на время обработки IN/OUT...

Как итог, будет доступно ровно 64кб оперативной памяти. А "Монитор", как и Windows, может занимать все 64кб теневой памяти. Где можно разместить сотни разных библиотек (математика, графика, архивация и т.д.)
Last edited by Paguo-86PK on 18 Mar 2015 12:17, edited 2 times in total.
User avatar
JeNNeR
Fanat
Posts: 52
Joined: 18 Nov 2014 09:17
Location: Отсюда

Re: Набросок РК-несовместимой версии

Post by JeNNeR »

Ты сейчас довольно точно описал работу со страницами памяти у процессора 65030 (если я правильно помню...) из приставки Атари.
Всё новое - это хорошенько забытое старое.
User avatar
Paguo-86PK
Maniac
Posts: 267
Joined: 12 Apr 2011 20:43
Location: Tashkent

Re: Набросок РК-несовместимой версии

Post by Paguo-86PK »

Эм-ммм...
1. Когда я изучал работу ВН59 (Микропроцессоры и микропроцессорные системы), если я не ошибся, понял, что ВМ80 настолько прост, что ВН59 сама ему отсылает команду call (CD xx xx). Разница в том, что счётчик команд PC при этом стоит на месте. Тем самым, в режиме генерации прерывания можно отправить не только одну команду call, но и десятки других арифметических, не двигая PC. Так ли?
Если так, значит, можно реализовать кучу возможностей. Например:

Code: Select all

40 86    - mov b,b + add m ; Здесь mov b,b ничего не производит, как холостая операция
---------- Данная конструкция работает так:
40       - генерирует прерывание
-- D3 80 - out 80h ; отправляем аккумулятор в буфер. push psw нельзя: стек жрёт такты
-- 78    - mov a,b ; загружаем регистр префикса (40 40)
--<86>   - add m   ; выполняем операцию префикса (86)
-- 47    - mov b,a ; помещаем результат в регистр префикса
-- DB 80 - in  80h ; восстанавливаем аккумулятор. pop psw нельзя: флаги АЛУ нужны также
---------- Тем самым, аппаратно реализована следующая команда:
40 86    - add b,m
То же самое и с другими трюками:

Code: Select all

40 29       - dad b,h    -> D3 80 79 85 4F 78 8C 47 DB 80
6D E6 AA    - ani l,0AAh -> D3 80 7D E6 AA 6F DB 80
64 3A 34 12 - ldh 01234h -> D3 80 3A 34 12 67 DB 80
И всё такое в этом духе.
Думаю, можно организовать так: Когда в активном M1 встречаются холостые пересылки (40; 49; 52; 5B; 64; 6D), генерируются сигналы прерывания, а к шине данных подключается крошечная ПЗУ с "псевдо-микрокодом":

Code: Select all

6D E6 AA    - ani l,0AAh -> D3 80 7D<00>6F DB 80<76>
64 3A 34 12 - ldh 01234h -> D3 80<00>67 DB 80<76>
Где <00> - выполнить одну операцию непосредственно и продолжить прерывание;
а <76> - отключить ПЗУ-"микрокода" и прекратить прерывания...

Здесь ПЗУ-микрокода - условно. Можно "подтянуть" теневое статическое ОЗУ малой ёмкости, где можно набивать любой код и, тем самым, реконфигурировать все комплексные команды в режиме реального времени...

 Реализация
Скажем, если холостые mov-пересылки будут генерировать такие адреса программ с
микрокодом:

Code: Select all

40 --:0000 - mov b,b
49 --:0010 - mov c,c
52 --:0020 - mov d,d
5B --:0030 - mov e,e
64 --:0040 - mov h,h
6D --:0050 - mov l,l
76 --:0060 - hlt
7F --:0070 - mov a,a
В сочетании с кодом команды будет формировать адрес:

Code: Select all

40 3A:3A00 - mov b,b + lda xxxx
49 3A:3A10 - mov c,c + lda xxxx
.. .. .... - ..................
40 E6:E600 - mov b,b + ani xx
49 E6:E610 - mov c,c + ani xx
То примерная прошивка микрокода будет выглядить, допустим, так:

Code: Select all

     .0 .1 .2 .3 .4 .5 .6 .7 .8 .9 .A .B .C .D .E .F|prefix+code
0700 D3 80 78 00 47 DB 80 76 -- -- -- -- -- -- -- --|40 07 -- --
0710 D3 80 79 00 4F D3 80 76 -- -- -- -- -- -- -- --|49 07 -- --
07.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..|.. .. .. ..
3A00 D3 80 00 47 DB 80 76 -- -- -- -- -- -- -- -- --|40 3A xx xx
3A10 D3 80 00 4F DB 80 76 -- -- -- -- -- -- -- -- --|49 3A xx xx
3A20 D3 80 00 57 DB 80 76 -- -- -- -- -- -- -- -- --|52 3A xx xx
3A30 D3 80 00 5F DB 80 76 -- -- -- -- -- -- -- -- --|5B 3A xx xx
3A40 D3 80 00 67 DB 80 76 -- -- -- -- -- -- -- -- --|64 3A xx xx
3A50 D3 80 00 6F DB 80 76 -- -- -- -- -- -- -- -- --|6D 3A xx xx
3A60 D3 80 00 77 DB 80 76 -- -- -- -- -- -- -- -- --|76 3A xx xx
3A70 -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --|7F 3A xx xx
.... .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..|.. .. .. ..
8000 D3 80 78 80 47 DB 80 76 -- -- -- -- -- -- -- --|40 80 -- --
8010 D3 80 79 80 4F DB 80 76 -- -- -- -- -- -- -- --|49 80 -- --
80.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..|.. 80 -- --
.... .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..|.. .. .. ..
E600 D3 80 78 00 47 DB 80 76 -- -- -- -- -- -- -- --|40 E6 xx --
E610 D3 80 79 00 4F DB 80 76 -- -- -- -- -- -- -- --|49 E6 xx --
E6.. .. .. .. .. .. .. .. .. .. .. .. .. .. .. .. ..|.. E6 xx --

Данную идею я реализовывал в том онлайн-эмуляторе.

Code: Select all

64 01 34 12 - lea bc,hl+1234h ; аналог x86 - lea cx,[bx+1234h]
40 DA 34 12 - orc bc,1234h    ; выполнить or bc,1234h если cf
52 CC 34 12 - andz de,1234h   ; выполнить and de,1234h если zf
2. Некоторые операции привязать к таймеру. Например, in 7Fh работает как WAIT и ожидает сигнала таймера (или ВГ75). При записи/чтения с магнитофона такая синхронизация была бы очень удобной (в ту эпоху конечно...)
Кстати, любопытная идея получается: Во время ввода/вывода на магнитофон, программировать ВГ75 на очень крошечный экран, чтобы число кадров в секунду увеличилось до пары тысяч. А чтением 0C001 и ani 20h - синхронизировать.
Хм, интересно, синтезатор можно ли так сделать без ВИ53? Настроить частоту кадров и частоту запросов ПДП - уже две частоты (полифония)))...
Или код первого символа знакоряда (после СИ) гасить и перенаправлять в ЦАП - можно строить звуковую дорожку прямо на экране.
1. или если кодом символа и номером строки адресовать ОЗУ аудио сэмплов;
2. или если символы псевдо-графики 03h/14h/17h выводить - частота до 30Гц...
3. т.к. знакогенератор не использует два старших бита, можно их использовать для управления бита звука в любой момент, привязывая его к позиции на экране. у РК символы 08h,0Ah,0Ch,0Dh,18h,19h,1Ah,1Fh - пустые и 8 штук. можно добавить старшие биты в восьми разных строках символов, чтобы точнее управлять звуком...
Так, программировать биты графогенератора так:
00xxxxxx - нормальная строка символа.
01xxxxxx - загрузить "1" в промежуточный триггер.
10xxxxxx - загрузить "0" в промежуточный триггер.
11xxxxxx - выгрузить бит из промежуточного триггера в защёлку излучателя звука.

P.S.: Как видно, этот мой "набросок" насыщен всякими техническими изощрениями. Я пытаюсь максимально задействовать все ресурсы: От холостых команд (40/49/52/5B/64/6D), до неиспользуемых старших битов знакогенератора. Чтобы ничего не проподало зря...
К тому же, идея использования битов знакогенератора не требует тотальной переработки РК: Подпаивается пара триггеров, логика и... Можно рисовать звук прямо на экране...
viv-pm
Novelist
Posts: 31
Joined: 17 Mar 2015 21:54

Re: Набросок РК-несовместимой версии

Post by viv-pm »

Однако, что можно заметить. Машина на ВМ80 с отображением квазидиска на
пространство стека общеизвестна - ЮТ-88.
Я точно знаю, что был контроллер на ВМ85 с разделением пространств команд
(ПЗУ 64КБайт) и данных/стека (ОЗУ 16КБайт), хотя для этого анализировались
сигналы IO/M, S0, S1 и код команды.
А вот для ВМ80 подобного не было, хотя вполне можно реализовать. Или я
просто чего-то не знаю?
VGrad
Maniac
Posts: 208
Joined: 18 Nov 2013 15:15
Location: все оттуда ;)

Re: Набросок РК-несовместимой версии

Post by VGrad »

viv-pm wrote:Или я просто чего-то не знаю?
Уже существуют процессоры 8088/8086 !!!
У них разделены сегменты кода, данных и стека.
viv-pm
Novelist
Posts: 31
Joined: 17 Mar 2015 21:54

Re: Набросок РК-несовместимой версии

Post by viv-pm »

Входы ПЗУ:
A0..A7: шина адреса данных ВМ85 AD0..AD7;
A8..A10: сигналы IO/M,S0,S1;
A11,A12: выход регистра состояний (надо выбрать ещё 2 байта команды, 1 байт, выбирать не надо).

Выходы ПЗУ:
D0: выборка ПЗУ программ;
D1: выборка ОЗУ данных;
D2: выборка устройств ввода/вывода;
D3..D5: не используются;
D6,D7: вход регистра состояний (регистр тактируется по снятию RD или WR).

Что принципиально мешает организовать подобное для ВМ80?
User avatar
Stan
Banned
Posts: 397
Joined: 04 Jan 2013 10:09
Location: 95.24.178.158

Re: Набросок РК-несовместимой версии

Post by Stan »

Paguo-86PK wrote:Как итог, будет доступно ровно 64кб оперативной памяти. А "Монитор", как и Windows, может занимать все 64кб теневой памяти. Где можно разместить сотни разных библиотек (математика, графика, архивация и т.д.)
Именно так давным-давно сделано в "Специалисте_МХ", в котором, если вынести переключатель страниц на IN/OUT, все страницы ОЗУ будут по целых 64кб.
И это всё работает быстро, на 2 МГц, безо всякой маниловщины и схемотехнически бесполезного онанизма.

Странно читать, что такое количество заумного технического задротства имеет такой скромный итоговый результат! :o
В таких случаях говорят:"Гора родила мышь!" :idea:
viv-pm
Novelist
Posts: 31
Joined: 17 Mar 2015 21:54

Re: Набросок РК-несовместимой версии

Post by viv-pm »

Stan wrote:
Paguo-86PK wrote:Как итог, будет доступно ровно 64кб оперативной памяти. А "Монитор", как и Windows, может занимать все 64кб теневой памяти. Где можно разместить сотни разных библиотек (математика, графика, архивация и т.д.)
Именно так давным-давно сделано в "Специалисте_МХ", в котором, если вынести переключатель страниц на IN/OUT, все страницы ОЗУ будут по целых 64кб.
И это всё работает быстро, на 2 МГц, безо всякой маниловщины и схемотехнически бесполезного онанизма.

Странно читать, что такое количество заумного технического задротства имеет такой скромный итоговый результат! :o
В таких случаях говорят:"Гора родила мышь!" :idea:
Специалист-МХ, Орион-128 - машины на ВМ80 с единым адресным пространством
команд/данных со страничной организацией. Речь идёт о том, разделялись ли
аппаратно в какой-нибудь машине на ВМ80 эти пространства?
User avatar
Paguo-86PK
Maniac
Posts: 267
Joined: 12 Apr 2011 20:43
Location: Tashkent

Набросок РК-несовместимой версии

Post by Paguo-86PK »

Stan wrote:Именно так давным-давно сделано в "Специалисте_МХ", в котором, если вынести переключатель страниц на IN/OUT, все страницы ОЗУ будут по целых 64кб.
И это всё работает быстро, на 2 МГц, безо всякой маниловщины и схемотехнически бесполезного онанизма.

Странно читать, что такое количество заумного технического задротства имеет такой скромный итоговый результат! :o
В таких случаях говорят:"Гора родила мышь!" :idea:
Ну, если Вы меня внимательно читали, я бы хотел полностью исключить всё из адресного пространства.
Устроить подобие "защищённого режима"-x86: Прикладному коду незачем копаться в портах аппаратуры. И незачем иметь доступ к служебным данным. Чисто 65536 байт доступного ОЗУ...
А вот "запрещёнными" в режиме пользователя инструкциями (hlt/in/out/di/ei) генерировать подобие "исключения"-x86: Передавать управление "системному коду".
1. Перед сбросом процессора:
1.1. Сохранить все регистры на случай, если надо узнать причину краха;
1.2. Загрузить в ОЗУ системы код BIOS (подобно описанному выше в РЕ3);
1.3. Обнулить указатель стека, чтобы BIOS знала про физический сброс.
2. Во-время "исключения" (команды 76, D3, DB, F3, FB):
2.1. Запросить ожидания Wait. Сгенерировать прерывание;
2.2. Сохранить "контекст" приложения: Все регистры занести в стек приложения:
2.3. Переключиться на стек системы.
3. Реконфигурировать ОЗУ отдельной маской. Каждую ячейку памяти спарить словом режима;
3.1. Младшая тетрада слова - режим чтения, старшая - режим записи;
3.2. Нулевой режим - обычное ОЗУ;
3.3. Для проекции ВВ55 в ОЗУ приложения на старые 8000..9FFF просто заполняем слова режима этого региона кодом нужного устройства;
3.4. У Радио-86РК область E000..FFFF при записи - ПДП, при чтении - ПЗУ. Младшую тетраду слова режима заносим код ПЗУ, старшую - ПДП.
(я так поступил в своём эмуляторе на Си: вместо дешифратора ОЗУ организовал дополнительные 64кб с кодами...)
Так систему можно гибко реконфигурировать в "Специалист", "Орион-128", "Микрошу" и т.д...
(хочу заметить, ОЗУ с маской режимов - не обязательно все 64кб. можно меньше - гранулировать: байт маски - на 16 байт маскируемого. тем самым, получим уже 16 страниц маски. можно переключать. мгновенно)

 Про маску (как работало в эмуляторе моём):
WR - Write/Read-mode
00 - Write-to-RAM / Read-from-RAM;
88 - Write-to-i8255 / Read-from-i8275;
CC - Write-to-i8275 / Read-from-i8275;
EF - Write-to-DMA / Read-from-ROM;

Заполнение ОЗУ дешифрации:
0000..7FFF - 00 - Ячейки ОЗУ;
8000..9FFF - 88 - Ячейки ВВ55;
C000..DFFF - CC - Ячейки ВГ75;
E000..FFFF - EF - Ячейки ПЗУ/ПДП.

Я понимаю, всё кажется путанным...
Но, если всё делать под современные реалии (сейчас не время дефицита - ПЛИС на любой вкус найти можно) и организовать собственный чипсет, то всё можно сделать...

Кстати. Когда у меня производительность была спартанской (Pentium-90MHz 48Mb-RAM), в среде LCC-Win32 нашёл способ быстрого скроллинга всего экрана (при сбое ВГ75/ВТ57): Просто, в режиме экрана 78x30 я заранее учетверял его до 156x60. Процедура ПДП считывала символы во все четыре позиции. Подсчитывал, на сколько символов в кадр уезжает ВГ75 и просто выводил тот регион...
Получался производительный и достоверный скролл.
Интересно, реализовано ли это в каком-то эмуляторе? А то что-то не встречал...