4-bit Processor

4-битные микроконтроллеры и микропроцессоры (прошлое, настоящее, будущее)

Moderator: Lavr

User avatar
Lavr
Supreme God
Posts: 16680
Joined: 21 Oct 2009 08:08
Location: Россия

Post by Lavr »

VituZz wrote:В моём понимании схемотехнически простой 4-битный процессор имеет 4-битный аккумулятор и 8-битный регистр счётчика команд, а также 16 инструкций (4 бита на КОп). Любое усложнение такой схемы (добавление префиксов команд, большое число регистров, введение стека) уже приводит к непропорциональному усложнению схемы.
...
Поэтому мне и кажутся интересными лишь два варианта: простой в моём понимании 4-разрядный проц или полноценный 8-разрядный.
Я полностью согласен с твоим мнением, но хочу еще переключатель банков, и префиксы - они не усложняют чрезмерно, стек - локальный в файле регистров - всё равно регистры общего назначения это отдельное ОЗУ.
Сильно распухнуть не должно.
User avatar
VituZz
God
Posts: 1343
Joined: 13 Nov 2010 04:06

Post by VituZz »

Возможно, твой вариант может быть аппаратно "снизу вверх" совместим с моим?
User avatar
Lavr
Supreme God
Posts: 16680
Joined: 21 Oct 2009 08:08
Location: Россия

Механизм рестартов

Post by Lavr »

Механизм рестартов

Поскольку наш проект с самодельным АЛУ на NAND близок к успешному завершению, я продумываю и другие вопросы, связанные с нашим 4-битым ЦПУ.

И один из вопросов, аппаратно затратных - это механизм прерываний, а мы сошлись во мнении, что прерывания необходимы. С этим вопросом тесно связан другой - вызовы подпрограмм и возвраты из них.

В оригинале схемы, которую я выбрал из-за её простоты, но, тем не менее, и некоторой функциональности, данный вопрос решен примитивно просто, хотя и вполне работоспособно.

В этой конструкции JMP ADDR ничем не отличается от CALL ADDR и приводит к переключению страниц (или сегментов). То есть, JMP ADDR происходит на смещение 0 указанного в ADDR сегмента.
Ещё "смелее" решен вопрос с возвратом из подпрограмм - это просто сброс программного счётчика в 0, то есть переход на ячейку с адресом 000H.
Прерывания не реализованы вовсе.

Это, конечно, всё работает, и даже можно счесть решение оригинальным для простой, но работающей модели ЦПУ, только в практической конструкции вряд ли применимо. :wink:

Мы привыкли, что адреса возвратов заносятся в стек, откуда и извлекаются по разным командам возврата. Но вот со стеком в этом проекте пока проблемы.

Поскольку для простоты мы склонились к Гарвардской архитектуре, оставив себе послабление, что в память программ возможна запись, то я пока простого механизма записи в ОЗУ, содержащее 12 бит КОП и 4 бита непосредственно данных, не вижу.
Даже табличные данные, похоже, придётся сделать как в PIC: через RET с загрузкой аккумулятора.

И основная проблема, что нужно бы задействовать двунаправленные шинные формирователи, а их в конструкции просто пока совершенно нет - что я, в общем-то, записываю в плюс простоте схемотехники.

Так вот, я предлагаю реализовать механизм прерываний и вызовов-возвратов через рестарты - то есть короткие переходы на фиксированный адрес, как RST N в i8080.
Под адреса рестартов выделить нулевой сегмент ОЗУ программ, размером в 256 байт.
Первые 3-4 этих адресов - выделить под аппаратные прерывания, а остальные - по сути - будут фиксированные точки возвратов из CALL ADDR, или просто переходы на фиксированный адрес в нулевом сегменте.

Работать всё это должно так.

Code: Select all

   JMP START; переход за границу 0-го сегмента.
   ...          ;      вектора переходов


ARET5:     ; фиксированный адрес перехода по RET5
   JMP ADDR_RET_SUB10; возврат к вызову SUB10

   ...          ;      вектора переходов



START:
   ...          ; что-то тут делаем в программе
   CALL SUB10
ADDR_RET_SUB10:  ; адрес возврата из SUB10



SUB10:
   ...      ; что-то тут делаем в программе
RET5     ; возврат по фиксированному адресу -> ARET5
Да, возможно механизм очень непривычный, но аппаратно реализуется довольно просто и всё ж более гибкий, нежели в оригинальной конструкции.

Это же избавляет от необходимости иметь где-то стек, но, похоже, накладывает ограничение, характерное для Фортрана - подпрограмму нельзя вызвать из самой себя, или что-то похожее связанное с вызовом в цикле.
В Фортране ранних машин стек также не использовался, а адрес возврата помещался в первые ячейки вызываемой подпрограммы, откуда и вызывался по RET.

В ЦПУ Гарвардской архитектуры необходим значительный набор регистров общего назначения (РОН) в роли памяти данных.
Как я упоминал уже - с этим есть проблема: на роль РОН у меня пока претендуют регистры К155ТМ8, по их 4-битности и доступности, но много таких корпусов в ЦПУ напихивать не хотелось бы, чтобы не раздувать простую конструкцию аппаратно.

Но, возможно, кто-либо знает другое - простое и оригинальное решение?
b2m
Devil
Posts: 905
Joined: 26 May 2003 06:57

Post by b2m »

Это получается, что SUB10 у тебя может вызываться только из одного места (START), раз уж она всегда туда возвращается. Суть подпрограмм как раз другая, чтобы они вызывались из разных мест и возвращались в разные места, откуда их вызвали. Если вложенность подпрограмм минимальна, то для адреса возврата можно сделать регистр. Но тогда подпрограмма не сможет вызывать другую подпрограмму. Можно, однако, сделать команду загрузки/сохранения этого регистра в память (типа как у DEC-оподобных процов). Тогда лишаемся только рекурсии. Если очень уж понадобится неглубокая рекурсия, то стек можно реализовать обычными командами (пересылкой памяти псевдо-стека).
Страничка эмулятора наших компьютеров
http://bashkiria-2m.narod.ru/
User avatar
Lavr
Supreme God
Posts: 16680
Joined: 21 Oct 2009 08:08
Location: Россия

Post by Lavr »

b2m wrote:Это получается, что SUB10 у тебя может вызываться только из одного места (START), раз уж она всегда туда возвращается. Суть подпрограмм как раз другая, чтобы они вызывались из разных мест и возвращались в разные места, откуда их вызвали. Если вложенность подпрограмм минимальна, то для адреса возврата можно сделать регистр. Но тогда подпрограмма не сможет вызывать другую подпрограмму. Можно, однако, сделать команду загрузки/сохранения этого регистра в память. Тогда лишаемся только рекурсии. Если очень уж понадобится неглубокая рекурсия, то стек можно реализовать обычными командами (пересылкой памяти псевдо-стека).
Ограничения есть - согласен с тобой. Но как я и сказал, это гибче, чем прототип, где все возвраты на адрес 000Н.

А вот регистров мне как раз и не хватает, чтобы даже просто пару вложений сделать обычным образом.

Если взять 8 РОН - это 8 корпусов микросхем. Один вызов подпрограммы из них "отъест" сразу 3, т.к. 12 бит программный счётчик.

В оригинале - всего 4 РОН в отдельной микросхеме ИР26 - но она нераспространённая.

Единственное - если добавить апаратно запись в ОЗУ программ на место данных, то в команде JMP ADDR можно будет ADDR изменить.

Регистров не хватает катастрофически - в чём вся и проблема.
Либо какое однокорпусное ОЗУ под них взять - но тоже не знаю распространённых экземпляров.
b2m
Devil
Posts: 905
Joined: 26 May 2003 06:57

Post by b2m »

Lavr wrote:Единственное - если добавить апаратно запись в ОЗУ программ на место данных, то в команде JMP ADDR можно будет ADDR изменить.
Можно сделать векторы RST парными, сначала идёт адрес возврата (который модифицируется при вызове этого RST), а затем идёт адрес подпрограммы. Т.е. RST 5 сохраняет пятый адрес возврата и вызывает пятую п/п, а RET 5, которым заканчивается пятая п/п, возвращается по пятому адресу возврата.
Страничка эмулятора наших компьютеров
http://bashkiria-2m.narod.ru/
b2m
Devil
Posts: 905
Joined: 26 May 2003 06:57

Post by b2m »

Если не хочется отходить от гарвардской архитектуры, таблицу адресов возврата можно сделать в сегменте данных.

Т.е. сегмент кода начинается таблицей п/п, а сегмент данных - таблицей возвратов из п/п.
Страничка эмулятора наших компьютеров
http://bashkiria-2m.narod.ru/
User avatar
Lavr
Supreme God
Posts: 16680
Joined: 21 Oct 2009 08:08
Location: Россия

Post by Lavr »

b2m wrote:
Lavr wrote:Единственное - если добавить апаратно запись в ОЗУ программ на место данных, то в команде JMP ADDR можно будет ADDR изменить.
Можно сделать векторы RST парными, сначала идёт адрес возврата (который модифицируется при вызове этого RST), а затем идёт адрес подпрограммы. Т.е. RST 5 сохраняет пятый адрес возврата и вызывает пятую п/п, а RET 5, которым заканчивается пятая п/п, возвращается по пятому адресу возврата.
Пожалуй, интересно - надо обдумать и прикидку сделать в "Протезе".

А в 155 серии мне помнится только одно статическое ОЗУ было - К155РУ5, ёмкостью 256 бит?
Но помнится, оно не было слишком распространённым...
b2m
Devil
Posts: 905
Joined: 26 May 2003 06:57

Post by b2m »

Code: Select all

К  155 РУ2   |  SN7489  | ТТЛ   ОК |  16*4  |    60   |  525   | 2.16/3
К  155 РУ5   |  93410DС |       ОК | 256*1  |    60   |  700   | 2.16/3
К  155 РУ7   |  93425АРС|       3С |  1К*1  |    45   |  700   | 2.16/3
             |  93475FС |          |  1К*4  |    35   | 1400   | 6.25/
Страничка эмулятора наших компьютеров
http://bashkiria-2m.narod.ru/
User avatar
Lavr
Supreme God
Posts: 16680
Joined: 21 Oct 2009 08:08
Location: Россия

Post by Lavr »

b2m wrote:

Code: Select all

К  155 РУ2   |  SN7489  | ТТЛ   ОК |  16*4  |    60   |  525   | 2.16/3
К  155 РУ5   |  93410DС |       ОК | 256*1  |    60   |  700   | 2.16/3
К  155 РУ7   |  93425АРС|       3С |  1К*1  |    45   |  700   | 2.16/3
             |  93475FС |          |  1К*4  |    35   | 1400   | 6.25/
Спасибо... но я просматриваю свои закрома.
Нашел вот единственную К155РУ5 и в сомнениях - вводить ли её в схему...
b2m
Devil
Posts: 905
Joined: 26 May 2003 06:57

Post by b2m »

Lavr wrote:Нашел вот единственную К155РУ5
4 бита за 4 такта собираешься считывать? :)
Для регистров РУ2 подходит.
Страничка эмулятора наших компьютеров
http://bashkiria-2m.narod.ru/
User avatar
Lavr
Supreme God
Posts: 16680
Joined: 21 Oct 2009 08:08
Location: Россия

Post by Lavr »

b2m wrote:
Lavr wrote:Нашел вот единственную К155РУ5
4 бита за 4 такта собираешься считывать? :)
Для регистров РУ2 подходит.
Да вот весь в сомнениях... РУ2 у меня нету - а значит и у других эти все РУ не самая популярная элементная база...
User avatar
VituZz
God
Posts: 1343
Joined: 13 Nov 2010 04:06

Post by VituZz »

РУ2 часто встречалась в старой аппаратуре, у меня есть пару десятков. РУ5 - более редкие, но штук шесть тоже есть. Посмотрел на аукционе - сразу на глаза попались два лота РУ2 и по смешной цене - от 0,5 до 2 грн за штуку (0,1-0,25$).
User avatar
Lavr
Supreme God
Posts: 16680
Joined: 21 Oct 2009 08:08
Location: Россия

Post by Lavr »

VituZz wrote:РУ2 часто встречалась в старой аппаратуре, у меня есть пару десятков. Посмотрел на аукционе - сразу на глаза попались два лота РУ2 и по смешной цене - от 0,5 до 2 грн за штуку (0,1-0,25$).
Посмотрел я тоже в каталоги - цена 8 руб. 50 коп. Только не знаю, сколь она реальная...
Завтра зайду в магазин - есть ли она просто в магазине радиодеталей, а то я как-то не очень доверяю интернет-торговле.

Наверное сразу надо спрашивать SN7489 и не морочить продавцам голову... :wink:
User avatar
Lavr
Supreme God
Posts: 16680
Joined: 21 Oct 2009 08:08
Location: Россия

RAM Data

Post by Lavr »

b2m wrote:
Lavr wrote:Единственное - если добавить апаратно запись в ОЗУ программ на место данных, то в команде JMP ADDR можно будет ADDR изменить.
Можно сделать векторы RST парными, сначала идёт адрес возврата (который модифицируется при вызове этого RST), а затем идёт адрес подпрограммы. Т.е. RST 5 сохраняет пятый адрес возврата и вызывает пятую п/п, а RET 5, которым заканчивается пятая п/п, возвращается по пятому адресу возврата.
b2m wrote:Если не хочется отходить от гарвардской архитектуры, таблицу адресов возврата можно сделать в сегменте данных.
Т.е. сегмент кода начинается таблицей п/п, а сегмент данных - таблицей возвратов из п/п.
Дмитрий - прикинул по схеме, немного не понял мысль, применительно к обстоятельствам...

Вот у нас ОЗУ программ - аналог ПЗУ программ как у PIC:

Image

То есть, мы договорились, что загружается программой оно извне, аппаратно, скажем через SPI.

Далее - при работе 4 бита поступают как данные на внутреннюю шину данных - в АЛУ или регистры.
12 бит инструкции поступают на ПЗУ микрокоманд и всякие дешифраторы кода.

Немного изменив схему, я могу заставить её в одну из RAM обратно записать 4 бита данных через шину данных (правда испорчу 4 бита кода операции, но кода, может, и 8 бит хватит).

То есть, как я и сказал - в команде JMP ADDR можно будет ADDR изменить - записать 4 бита.
Но биты кода операции мне не доступны через шину адреса и усложнять сильно я пока не хотел.
Значит биты кода JMP мне не доступны.
Так можно менять таблицы данных, которые сделаны по типу PIC: RETA - возврат с загрузкой 4 бит данных в аккумуляторе.

Но как тут реализовать твою идею - я несколько затрудняюсь...
Не пояснишь в виду "живой" схемы?