středa 15. srpna 2012

Tranzistorová aritmeticko logická jednotka

Vždycky jsem si říkal, že pochopím, jak doopravdy funguje procesor teprve, až ho budu moci sám postavit.
Doba pokročila a bláznivé plány se přiblížily skutečnosti. Zapojení, schemata a fotky rozhodně nemají být návodem ke konstrukci, spíš pouze inspirací, co všechno se dá postavit a jak to může být jednoduché, případně složité.
Úplně prvním impulzem ke stavbě bylo toto zapojení: http://www.cs.ubc.ca/~hilpert/e/ABC/asm.html
Jednobitová úplná sčítačka-odčítačka realizovaná čtrnácti systémy triod s odporovými děliči na mřížkách, tvořící NAND a NOR hradla podle volby poměru odporů. Schema je z roku 1940.
Stavět to dnes z elektronek by bylo sice hezké, ale bylo by to víc práce, než že by výsledkem bylo něco smysluplného v dohledné době. Jen osm stejných sčítaček (limit pro smysluplný procesor) by bylo plato 40 dvojitých triod a to by neumělo samo vlastně nic, ikdyž bych ho stavěl týdny.
Zapojení jsem tedy překreslil pro tranzistory a odměřil vhodné odpory pro napájecí napětí 12V. Byl jsem až překvapen, jak dobře ty hradla z jediného tranzistoru a čtyř odporů chodí.

Zvolil jsem variantu sčítačky z NAND hradel, která je snad nejúspornější, co se počtu součástek týče. T1-T4 a T5-T8 realizují funkci EXOR hradel. Díky tomu, že jsou přístupné spoje NAND hradel uvnitř EXOR, je jednoduché realizovat přepínání mezi režimem sčítání a odčítání, prostě volbou odebírání signálu "Carry/borrow" - přenos do vyššího řádu - buď tranzistorem T9 nebo T10. Dvojice odporů navíc před výstupním T8 slouží k odpojení sčítačky od výstupní sběrnice při nepřivedení signálu pro sčítání ani odčítání. (Na výstupu bude log. 1 i když na vstupech A, B, C in cokoli.)

Chvilka práce a první sčítačka byla hotová (ještě varianta s 33K a bez možnosti odpojení od sběrnice):
Fungovala perfektně na první zapojení. Deska je zakončená konektorem, aby se dala pospojovat se zbytkem budoucího zapojení. Sčítačku jsem testoval i při provozu na vyšších frekvencích, výstup sumy fungoval cca do 1MHz, výstup přenosu hůř. Velké vazební odpory spolu s kapacitou báze tvoří RC články a tranzistory od určité frekvence zůstávají otevřené. Pomůže snížení napájecího napětí resp jeho přesnější nastavení, protože se vzrůstající frekvencí se zužuje rozpětí napájecího napětí, při kterém hradla fungují správně. Staticky fungují pro 1K a dvakrát 22K děliče asi od 9,5V do 14V. Na 1MHz jen mezi 11,5V a 11,75V pro představu. Původní realizace NOR hradla pomocí 1K a 33K odporů maximální frekvenci ještě snížila, proto jsem pak zvolil variantu s 22K 1% vazebními všude a mezi bázi a emitor pak 2K2 pro dvouvstupový NOR a 1K pro dvouvstupový NAND. Kolektorové odpory jsem nechal 2K2, aby zapojení moc netopilo. I tak bere jediná sčítačka 25mA.
Hradla z odporové logiky: (více než tři vstupy je kvůli spolehlivosti lepší řešit diodami)

Přešel jsem na menší rozměr odporů a další desky už vyšly o něco menší a díky lepším tolerancím odporů a množství tranzistorů stejné série chodí všechny naprosto shodně.

Tranzistory jsem musel vybírat podle ceny a dostupnosti v obchodech a z možných vybral ty, co mají nejmenší kapacitu báze - 2N3904, ty fungovaly nejlépe (lépe než C945 a mnohem lépe než BC548).
Dělat ručně najednou 8 stejných desek by bylo bláznovství, navíc jsem zapojení předělával, a tak jsem mezitím začal navrhovat další části budoucího zapojení. Když už ty sčítačky tak hezky fungují, tak aby alespoň k něčemu byly.
Když jsem věděl jak udělat spolehlivě NAND a NOR hradla, tak už byl zbytek zapojení prakticky jasný, až na to, co tam má vlastně být.
Postupně jsem tak nějak vymýšlel a hledal, co by to mělo umět a jak by jednotlivé části měly vypadat. Základní představu jsem znal ze školy, a tak šlo hlavně o to, vymyslet to tak, aby se z teorie a obrázků stal skutečně fungující celek.
Bloková představa:
Aritmeticko logická jednotka - ALU - může najednou dělat jen jednu operaci. K tomu potřebuje, aby na obou vstupech byla přítomná logická hodnota a registr na výstupu byl připravený načíst hodnotu výslednou. Registry zde označené A, B, Y se většinou v nákresech procesorů uvádějí jako pomocné, nebo se nekreslí vůbec - jsou součástí ALU - nezbytnou k funkci.
Vize byla taková, že bude jedna deska na které bude vnitřní sběrnice vstupů A, B a výstupů Y, povede od konektoru ke konektoru a do nich budou nastrkané desky logiky, co budou obstarávat jednotlivé funkce po přivedení řídících signálů z řadiče. Bez signálu se desky měly chovat, jakoby nebyly osazeny. Tento "třetí" stav je držen rezistory jako log. 1, všechny desky mají tedy výstupy typu otevřený kolektor.
Podrobněji jednotlivé desky:
Zapojení jsem neměl takto navrženo odzačátku, jak jsem ladil jednotlivé desky, zjišťoval jsem postupně, jak by to vlastně mělo vypadat. Příkladem nejasnosti konstrukce je například návrh základní desky v době, kdy jsem vůbec netušil, jak bude vypadat řadič a řídící vstupy desek prostě vyvedl na konektor, kolem kterého jsem nechal místo, aby se tam vešla jakkoli široká deska, co jsem myslel, že tam bude muset být.
Po pár týdnech vymýšlení sestavy příkazů mi došlo, že na realizaci řadiče stačí čtyři tranzistory jako dekodér 1 ze 4 a řada diod 1N4148. Deska pak vyšla jen o pár mm širší než onen, do prostoru osazený, konektor.
Koncepce je hodně amatérská především proto, aby se s tím dalo hrát hned od začátku. Jednotlivé desky jsou samostatně fungující celky a díky přímému řízení vnitřních registrů pomocí příkazů se s hotovou ALU dá komunikovat ve statickém režimu prostě jen přepínáním log. hodnot.
Celek:
Desky popořadě: Spínač Y registru ke sběrnici, registry Y, A, B, detekce nuly, rotace vpravo, vlevo, logika NAND/NOR/INV, 8-bit sčítačka-odčítačka s osazenými osmi jednobitovými sčítačkami-odčítačkami Deska zvlášť nahoře je řadič, od kterého vedou spoje k jednotlivým deskám.
Schema jednotlivých částí:
Výstupní registr Y s výstupním spínačem a datovou sběrnicí:
Vstupní registry A, B
 Deska rotace vpravo + řízení:
Deska logiky:
 Řadič ALU:
Úplně největší problémy jsem měl s těmi třemi registry. To je jediná deska, kde je potřeba sekvenční logika i při statickém provozu. Pro přepis log. hodnoty v registru je totiž třeba, aby se nejprve resetoval, nastavili se všude jedničky a ty se pak teprve dají přepsat na nuly. Ale k řízení je jen jeden přívod, kterým registru řeknu, že prostě chci zapsat novou hodnotu. Jednoduše je třeba, aby resetovací signál skončil dříve než signál pro zápis. O to se stará vazební kondenzátor. Při malé kapacitě se neresetují všechny bity a to ještě v závislosti na napájecím napětí. Pomůže zvedat kapacitu tak dlouho, až registr funguje spolehlivě, ale příliš velká kapacita způsobí zase omezení maximální provozní frekvence. Signál pro zápis musí trvat určitou dobu, aby se kondenzátor nabil a přestal držet všechny bity v log. 1, aby se stihly ještě zapsat nuly tam, kde mají po odpojení signálu zápisu být.
Pro budoucí běh se zdrojem taktovací frekvence bude lepší RC články zrušit a registr resetovat prostě polovinou periody časovacího signálu, protože z pohledu logických obvodů to není nic jiného než osmkrát klasický RS klopný obvod.
Pár fotek konstrukce:
základní deska ALU
 osazená deska ALU
Šasi s ALU, zobrazovačem a primitivní klávesnicí pro zadávání dat a příkazů
Zobrazovač je funkcí velmi primitivní, ale konstrukcí velmi složitý obvod. Převod 8-bit binární hodnoty na 3-místný BCD kód, tj tři dekadická místa vůbec není triviální. Použil jsem toto řešení pomocí sedmi kaskádně řazených modulů 4-bitových přičítaček tří pro vstupní číslo větší než 4: http://www.johnloomis.org/ece314/notes/devices/binary_to_BCD/bin_to_bcd.html
Zobrazovač je navržen pro zobrazování 0-255 a připraven na přepnutí do režimu aditivního kódu, tj zobrazování -128 až +127, na to je ale potřeba udělat ještě osmibitovou přičítačku čísla 127, která se připojí před celý modul zobrazovače (destička se dvěma obvody 74LS283 např.)
Desky zobrazovače:
Zadávání dat a příkazů jsem prozatím vyřešil primitivní klávesnicí. Desky paměti, programového čítače a řízení skoků jsou zatím ve stavbě, takže pro ověření momentální funkce to stačí.
Schema:

Zapojení se skládá z osmi RS klopných obvodů a dvou 8-bit D střadačů. NAND hradla slouží jen kvůli tomu, aby se uložená data připojila na datovou sběrnici ALU jen v případě zápisu do jejích registrů a ne jindy, např. při čtení výstupu. Jednoduché zapojení tak umožňuje plně ovládat tranzistorovou aritmeticko logickou jednotku.
Periferní obvody jsem nechtěl už dělat z tranzistorů, protože je to vcelku nuda. Zobrazovač by se redukoval na metr dlouho lištu diod a tranzistorů, co by přímo vytvářely logický můstek mezi osmi dráty sběrnice a dvaceti dráty segmentovek. To je například naprosto nepředstavitelné, na rozdíl od celé dosavadní stavby. Stejnětak místo čtyř obvodu 7474 jsem mohl osadit 16 tranzistorů a 64 odporů stejně jako v desce Y registru a místo D střadačů totéž plus dvakrát desku výstupních spínačů po osmi tranzistorech.
Ovšem volba TTL logiky přinesla vtipný problém, jak ji propojit s ALU, která má celá palubní napětí 12V. Navíc na datové sběrnici je potřeba spolehlivý obousměrný provoz kvůli budoucímu připojení paměti. Nakonec jsem navrhl kupodivu velmi jednoduché zapojení s jedním tranzistorem na každý bit, které funguje naprosto perfektně:

Tranzistory jsou zapojeny se společnou bází, na kterou mají přivedeno napětí asi 1,2V ze stabilizátoru. Tím je vytvořena rozhodovací úroveň asi 0,6V ze strany 5V logiky kdy jsou v nule tranzistory otevřené a převedou tak nulu na stranu 12V logiky nebo naopak zavřené a na 12V straně je log. 1 držená rezistory na výstupní sběrnici ALU (nejsou ve schematu). Opačným směrem, tj. z 12V logiky na 5V logiku funguje zapojení prostě jako dělič 2K2 ku 470R. Odpory 470R spolehlivě udrží log. nulu vstupu TTL a log. 1 vznikne přivedením 12V do děliče se sběrnice.
Zapojení sice nesplňuje teoretické požadavky na bezpečné definování logických hodnot TTL vstupů, ale v praxi s tím není vůbec problém (stejnětak kupodivu není problém například napájet dosavadní směs starých TESLA TTL74, nových TTL LS, HCT a HC napětím i jen 3,3V při kterém už vše komplet funguje.)
Část, co připojuje příkazovou sběrnici, není zakreslená, protože jsou to jen tranzistory v zapojení se společným emitorem na mínusu a jen invertují přivedený signál, proto má "klávesnice" invertovaný výstup příkazů.
Celek po vydrátování a zabudování stabilizátoru 5V:

Celé zapojení zatím bere 800-1200mA při 12V (včetně TTL za 5V stabilizátorem) podle poměru nul a jedniček uložených ve vstupních registrech.
Příkazy ALU:
Příkaz ; Princip ; binární zadání do řadiče (0, 0, 0, x, y, a, b, c)
1) Zápis do registru A  0 0 0 1 0
2) Zápis do registru B  0 0 0 0 1
3) Výstup Y na sběrnici   0 0 1 0 0
4) Y => A  0 0 1 1 0
5) Y => B  0 0 1 0 1

6) NAND (A,B) => Y  0 1 1 0 1
7) NOR (A,B) => Y   0 1 1 1 1
8) INV (A)=>Y ; NOR (A,0)  0 1 1 1 0

9) A+B=>Y ; ADD (A,B,0)  1 1 0 1 1
10) A-B=>Y ; SUB (A,B,0)  1 1 1 0 1
11) A+1=>Y ; ADD (A,0,1)  1 1 0 1 0
12) A-1=>Y ; SUB (A,0,1)  1 1 1 0 0
13) EXOR (A,B)=>Y ; SUB+ADD (A,B,0)  1 1 1 1 1

14) Bn => Yn+1 , B7 => Y0 , B7 => C  1 0 0 1 0     z registru B
15) Bn => Yn+1 , 0 => Y0 , B7 => C   1 0 0 1 1
16) Bn => Yn+1 , 1 => Y0 , B7 => C  1 0 1 1 1

17) An => Yn-1 , A0 => Y7 , A0 => C  1 0 1 0 0    z registru  A
18) An => Yn-1 , 0 => Y7 , A0 => C   1 0 0 0 1
19) An => Yn-1 , 1 => Y7 , A0 => C   1 0 1 0 1

Budoucí rozšiřování zapojení:
Programový čítač (vpravo) a deska řízení skoků (vlevo)
Programový čítač umožňuje postupné čtení příkazů z programové paměti, reset a paralelní zápis nové hodnoty.
Do konektorů programového čítače přijde kromě desky pro řízení skoků ještě deska "vracecích registrů" - nevím jak to teď jinak nazvat - které si budou pamatovat předchozí polohy programového čítače, což je nutné pro realizaci cyklů a podmíněných příkazů.
Výstupní konektor desky programového čítače bude navazovat na desku s programovou a datovou pamětí, která bude dále připojena přímo do ALU připraveným konektorem na desce 5/12V převodníku.

10.1.2013 Konečně osazena deska datové a programové paměti a desky programového čítače, jeho řízení a desky ručního ovládání. Po dnech ladění sekvenční logiky monstrum konečně umožňuje ruční zápis i úpravu programu a jeho běh, aspoň co se týče jednoho dokola běžícího cyklu.
ukázky:
http://www.youtube.com/watch?v=vlDIFTJoWj8
http://www.youtube.com/watch?v=f0YFwWl0J8Q
Přibyly také dvě desky ručního ovládání - deska pro ruční zápis programu a zdroj časovacího signálu umožňující ruční krokování

 Schema desky datové a programové paměti
Deska automatického řízení čtení a zápisu do datové paměti. Derivační obvod dole slouží ke zpoždění načtení příkazu do příkazového registru ALU (na desce datové a programové paměti).
 Ruční ovládání programové paměti (inspirace: http://members.chello.cz/danhard/tlacitko.gif )
 Programový čítač
 Ukázka jak by se sekvenční logika neměla dělat: Kvůli přepínání klopných obvodů vznikají v některých signálech mezery, co byly potřeba dodatečně odstraňovat pomocí RC článků.

 Aneb když se nedaří: Výstup paměti zatížený diodovými hradly - poslední schema 2. bit (taktování cca 500kHz)

29.1.2013
Konečně se dostalo na úpravu tranzistorových registrů ALU tak, že se resetují poslušně časovacím signálem. Jediný drobný problém byl ale fakt, že změna časovacího signálu nastane dříve, než změna příkazu ALU, takže bylo zapotřebí časovací signál pro registry oddělit a zpozdit. První varianta byla ho poslat skrz D - klopné obvody registru příkazu, kde zpoždění již úmyslně vzniká. Ale to nestačilo. Přidaný tranzistor osazený přímo místo vazebního kondenzátoru se otevíral stále dříve, než se stihly zavřít tranzistory ovládající registr přes diodový řadič ALU. Potřebné zpoždění dokázala vytvořit až šestice zasebou spojených invertorů 7404. Ale s tím už registry načítají naprosto bez chyb. Konečně.
Schema upravených registrů A,B
Schema upraveného registru Y.

Literatura:
Matoušek, D.: Číslicová technika. 1. vyd. Praha, BEN 2001 ISBN 80-7300-025-3
Jedlička, P.:Přehled obvodů řady 7400. 1. vyd. Praha, BEN 1997 ISBN 80-86056-08-2
Kubica, L.:Přehled diskrétních polovodičových součástek TESLA. 2. vyd. Praha, BEN 2002 ISBN 80-7300-061-X
Příruční katalog elektronek a polovodičových prvků TESLA Rožnov. 2. vyd Ostrava 1972.
http://www.cs.ubc.ca/~hilpert/e/ABC/asm.html
http://www.johnloomis.org/ece314/notes/devices/binary_to_BCD/bin_to_bcd.html
http://www.circuitstoday.com/ripple-carry-adder
http://www.ohradni.cz/instrukce_8080.pdf

3 komentáře:

RayeR řekl(a)...

Tak to je docela hardcore konstrukce :) Do toho bych nesel, to zabere hrozne casu, kdyz uz tak bych stavel z 74xx logiky. Radic se da udelat z EPROM se zpetnou vazbou...

Problem s temi pametovymi registry snad vyresi nabezna a sestupna hrana hodin. Sem zvedavej na tu pamet, jesi bude taky z tranzistoru a diodova matice programu :) To asi ne, ale bylo by k tomu docela stilovy pribastlit feritovou pamet, kera ma jednu velkou vyhodu, ze si pamatuje i po vypnuti.

Arambajk řekl(a)...

Přesně tak, až bude zdroj časovacího signálu tak ho přivedu i k těm registrům, takhle je to příliš nespolehlivé. Navíc mi vzniká problém při sčítání čísel, co procházejí skrz carry u sčítaček a vlivem zpoždění mi poslední sčítačky načítají občas špatnou log. hodnotu, protože reset registru trvá zřejmě pořád příliš krátkou dobu.

Paměť dám klasicky cache ze 486 a kolem TTL logiku.. měl jsem sice před časem takový nápady jako dělat matici z keramik v serii s doutnavkama a postavit k tomu řízení, ale potíž je, že bych chtěl aby to aspoň něco umělo a dělat rozumnější kapacitu paměti skoro jakýmkoli způsobem je naprosto šílená práce:)

Anonymní řekl(a)...

Vstupni registr pro rucni ovladani byval vyuzivan mnohem vsestraneji.
Byl s indikaci stavu, takze se dal pouzit i pro vystup.
Samozrejme binarni :)
V rucnim rezimu se s nim dal cist a zapisovat stav systemovych registru.
Zkuste se podivat pro inspiraci treba na pocitace rady HP21MX.
Obsluha bezne psala z hlavy pres S registr kratke obsluzne programy periferii a systemovi programatori si pamatovali diskovy zavadec potrebny na nastartovani systemu.