CPU-hemmabygge
Re: CPU-hemmabygge
Hur få instruktioner man kan klara sig med är defintivt något jag funderat över. Någon konklusion/idé?
Man kan ju även minska antalet bitar, t.ex 4-bit istället för 8-bit osv.
Man kan ju även minska antalet bitar, t.ex 4-bit istället för 8-bit osv.
- anders_bzn
- Inlägg: 5724
- Blev medlem: 17 december 2008, 19:22:18
- Ort: Kävlinge
- Kontakt:
Re: CPU-hemmabygge
En vilkorad hoppinstruktion kan vara bra. Eller ännu enklare, skippa nästa instruktion om föregående aritmetiska insteuktion blev noll.
- Spisblinkaren
- EF Sponsor
- Inlägg: 12990
- Blev medlem: 13 december 2012, 21:41:43
Re: CPU-hemmabygge
Hej gkar!gkar skrev:Skift åt höger är ofta onödig. Addition med sig själv ger samma sak.
Skift åt vänster är bra om det finns både aritmetisk och logisk.
Addc är en bra tanke om man åker 8 bitar.
Sedan kan man ju implementa det så att det alltid skiftas in/ut X-flagga eller så om man vill.
Kan du förklara skillnaden mellan aritmetiskt och logiskt skift? Jag har faktiskt bara kallat dom logiska utan att tänkt det minsta på vad det egentligen innebär.
Dessutom, vad är X-flagga?

MVH/Roger
- Spisblinkaren
- EF Sponsor
- Inlägg: 12990
- Blev medlem: 13 december 2012, 21:41:43
Re: CPU-hemmabygge
Den är intressant.blueint skrev:Hur få instruktioner man kan klara sig med är defintivt något jag funderat över. Någon konklusion/idé?
Man kan ju även minska antalet bitar, t.ex 4-bit istället för 8-bit osv.
Jag tror jag har 36 men jag är inte säker såhär på rak arm.
Och då finns det ofta typ två instruktioner av samma slag (extended+immediate i mitt Motorola-inspirerade fall).
Så om man hoppar över det faktumet är antalet unika instruktioner inte mycket fler än 20.
Jag vet inte hur långt jag kommer på det men jävlaranamma, jag ska göra massor med försök!
Förhoppningsvis, för just nu har min CPU bara uppvisat tämligen primitiva livstecken:
Den interna initiala RST-instruktionen körs med galans.
Dvs POR funkar och adressbussen intar rätt värde starx efter spänningstillslag (POR).
Adressen blir då FFFEh.
Sen händer nåt ännu roligare.
CPU'n går ut och läser programminnet som jag dessutom lyckats programmera korrekt.
Två konsekutiva läsningar (adress FFFEh+FFFFh) sätter tom så småningom startadressen till den programmerade dvs 9000h
Därefter stegas faktiskt testprogrammet upp!
9000: C6 :LDA $, ratta in 01 på I/O
9001: 40
9002: 00
9003: A1 :CMP #
9004: 01
Alla de fyra första stegen gås igenom datamässigt (dvs adresser och data är korrekta). Dock utförs inte LDA $. Och vid adress 9003h så spårar CPU'n ur.
Noggrann analys visar att op-koderna C6 och A1 inte latchas in ordentligt i instruktionsregistret (IR). Dvs det är något fel i CPLD-programmet.
Fast det är klart, vad kan man förvänta sig när arkitekturen är inspirerad av en tvättmaskin

MVH/Roger
Re: CPU-hemmabygge
gkar skrev:Skift åt höger är ofta onödig. Addition med sig själv ger samma sak.
Skift åt vänster är bra om det finns både aritmetisk och logisk.
Du menar väl tvärtom? Skift åt vänster är samma som att addera med sig själv.
Re: CPU-hemmabygge
När det gäller vänsterskift är aritmetiskt och logiskt samma sak.
Nollor fylls på från höger.
Däremot vid högerskift så skiljer det sig.
Logiskt skift åt höger fyller på med nollor från vänster medans
aritmetiskt skift fylls på med samma bit som redan finns i den mest signifikanta biten, alltså nollor eller ettor.
Man kan säga att den högsta biten aldrig ändras.
På så sätt behåller man negativa tal som negativa.
Nollor fylls på från höger.
Däremot vid högerskift så skiljer det sig.
Logiskt skift åt höger fyller på med nollor från vänster medans
aritmetiskt skift fylls på med samma bit som redan finns i den mest signifikanta biten, alltså nollor eller ettor.
Man kan säga att den högsta biten aldrig ändras.
På så sätt behåller man negativa tal som negativa.
Re: CPU-hemmabygge
... och dessutom finns ju både skiftning och rotering med och utan flaggor inblandade ...
- Spisblinkaren
- EF Sponsor
- Inlägg: 12990
- Blev medlem: 13 december 2012, 21:41:43
Re: CPU-hemmabygge
Tack för den informationen. Nu är det glasklart!bit96 skrev:När det gäller vänsterskift är aritmetiskt och logiskt samma sak.
Nollor fylls på från höger.
Däremot vid högerskift så skiljer det sig.
Logiskt skift åt höger fyller på med nollor från vänster medans
aritmetiskt skift fylls på med samma bit som redan finns i den mest signifikanta biten, alltså nollor eller ettor.
Man kan säga att den högsta biten aldrig ändras.
På så sätt behåller man negativa tal som negativa.

Dock undrar jag fortfarande vad som krävs för MUL/DIV.
Jag kan alltså bara skifta in nollor åt båda hållen och ingen gång kan jag ta hänsyn till högsta biten (i min nuvarande implementation).
Hur långt kommer jag med det?
Man borde ju kunna begränsa sig till strängt positiva tal.
Man borde liksom kunna säga att här har vi ett negativt tal (på tvåkomplementform) men vi struntar i det och tolkar det som positivt (0-255 i mitt fall).
Sen borde man kunna göra det negativt i "efterhand" (om det nu ska bli ett "negativt" resultat).
Apropå det så har jag implementerat en egen skojig, men förmodligen ganska onödig, instruktion. Denna instruktion heter NOT och är 1-komplementet, dvs inversen, av talet.
Kan kanske komma till nytta här?

Ska vi börja med en MUL-algoritm?
Nån som är sugen?

MVH/Roger
Re: CPU-hemmabygge
Jajjamensan, du har helt rätt!haklu skrev:gkar skrev:Skift åt höger är ofta onödig. Addition med sig själv ger samma sak.
Skift åt vänster är bra om det finns både aritmetisk och logisk.
Du menar väl tvärtom? Skift åt vänster är samma som att addera med sig själv.
- Spisblinkaren
- EF Sponsor
- Inlägg: 12990
- Blev medlem: 13 december 2012, 21:41:43
Re: CPU-hemmabygge
Hur menar ni med att vänsterskift motsvarar addition med sig själv?
Förutsatt man skiftar in en nolla så multiplicerar man väl talet med två?
Vänta nu, multiplikation med två blir ju som att addera med sig själv!
Nu förstår jag också
MVH/Roger
Förutsatt man skiftar in en nolla så multiplicerar man väl talet med två?
Vänta nu, multiplikation med två blir ju som att addera med sig själv!

Nu förstår jag också

MVH/Roger
- Klas-Kenny
- Inlägg: 11765
- Blev medlem: 17 maj 2010, 19:06:14
- Ort: Växjö/Alvesta
Re: CPU-hemmabygge
Och vad är nu skillnaden mellan att addera med sig själv, och att multiplicera med två?
1+1 = 2*1
Edit: Och där kom du på det ja..

1+1 = 2*1
Edit: Och där kom du på det ja..

Senast redigerad av Klas-Kenny 24 februari 2013, 20:22:04, redigerad totalt 1 gång.
- Spisblinkaren
- EF Sponsor
- Inlägg: 12990
- Blev medlem: 13 december 2012, 21:41:43
Re: CPU-hemmabygge
Tack!blueint skrev:Kika här: enwp: Division algorithm#Fast division methods
Den här tycker jag var intressant:
https://en.wikipedia.org/wiki/Division_ ... _remainder
if D == 0 then throw DivisionByZeroException end
Q := 0 initialize quotient and remainder to zero
R := 0
for i = n-1...0 do where n is number of bits
R := R << 1 left-shift R by 1 bit
R(0) := N(i) set the least-significant bit of R equal to bit i of the numerator
if R >= D then
R = R - D
Q(i) := 1
end
end
Unsigned integers, obs.
Vänsterskift med 0 ingår. Det har jag (LSL).
Subtraktion ingår (jag har implementerat subtraktion på tvåkomplementsform (SUB) men frågan är vad det betyder i sammanhanget. Här fattar jag egentligen ingenting

Villkorssnurror har jag (endast BEQ, BNE, BPL och BMI dock). BEQ=Branch if EQual...
Maskning har jag (XOR, AND, OR och "NOT")
Re: CPU-hemmabygge
Precis, och det är ju ofta så man skriver kod i Assembler, eller bra kompilatorer gör det år en.
Arm är ju populärt för tillfället...
Source i R0, dest i R1.
2 add r1, r0, r0
3 add r1, r0, r0 lsl #1
4 mov r1, r0 lsl #2
5 add r1, r0, r0 lsl #2
7 rsb r1, r0, r0 lsl #3
8 mov r1, r0 lsl #3
9 add r1, r0, r0 lsl #3
if (a){
b *= 5;
} else {
b *= 7;
}
movs r0, r0
addne r1,r1,r1 lsl #2
rsbeq r1,r1,r1 lsl #3
rsb står för reverse subtract.
Dock är det inte säkert att det alltid lönar sig med längre mov, add, sub, rsb sekvenser då man brukar ha en singlecycle multiplikator numera. Dock brukar dom ha rätt lång latency så man riskerar bubblor i pipelinen. Åker man sedan en superskalär CPU och inte har bråttom kan man ofta sprida ut sin "diskreta" multiplikation över ett helt basicblock, och på så sätt få ner cykelåtgången i praktiken till noll.
Arm är ju populärt för tillfället...
Source i R0, dest i R1.
2 add r1, r0, r0
3 add r1, r0, r0 lsl #1
4 mov r1, r0 lsl #2
5 add r1, r0, r0 lsl #2
7 rsb r1, r0, r0 lsl #3
8 mov r1, r0 lsl #3
9 add r1, r0, r0 lsl #3
if (a){
b *= 5;
} else {
b *= 7;
}
movs r0, r0
addne r1,r1,r1 lsl #2
rsbeq r1,r1,r1 lsl #3
rsb står för reverse subtract.
Dock är det inte säkert att det alltid lönar sig med längre mov, add, sub, rsb sekvenser då man brukar ha en singlecycle multiplikator numera. Dock brukar dom ha rätt lång latency så man riskerar bubblor i pipelinen. Åker man sedan en superskalär CPU och inte har bråttom kan man ofta sprida ut sin "diskreta" multiplikation över ett helt basicblock, och på så sätt få ner cykelåtgången i praktiken till noll.