Design av en feltolerant RISCprocessor
|
|
|
- Georg Viklund
- för 10 år sedan
- Visningar:
Transkript
1 Design av en feltolerant RISCprocessor ANDREAS SÖDERBERG TOMAS HOLMGREN Examensarbete Civilingenjörsprogrammet för Elektroteknik CHALMERS TEKNISKA HÖGSKOLA Institutionen för datorteknik Göteborg 2003
2 Abstract The purpose of this master thesis work was to design a single-channel microprocessor for use in applications with high safety requirements. In order to fulfill the application requirements, the processor was designed to be fail silent. The microprocessor was designed using VHDL and was implemented in a pre-made FPGA target system called FPGA-labkortsystem, which was provided by Chalmers University of Technology. To demonstrate the microprocessor's functionality, a simple two-hand manoeuvre control was built, which controls a 230V power connection. To program the microprocessor, an assembler was developed in the programming language ADA. The assembler translates assembly language for the microprocessor into machine code, which is automatically inserted either into a VHDL ROM block used for simulation or into a script-file which is compatible with the programming environment for the FPGA target system. The result of the thesis work is a microprocessor which complies with the fail silence requirements according to a failure mode and effects analysis (FMEA) performed. In order to verify that the actual implementation of the microprocessor complies with the requirements, a complete assessment including fault injection should also be performed. However, such an assessment was not within the time limits set for the thesis work. Innehållet i detta häfte är skyddat enligt Lagen om upphovsrätt, 1960:729, och får inte reproduceras eller spridas i någon form utan medgivande av författaren. Förbudet gäller hela verket såväl som delar av verket och inkluderar lagring i elektroniska och magnetiska media, visning på bildskärm samt bandupptagning. Andreas Söderberg och Tomas Holmgren, Göteborg
3 Innehållsförteckning Abstract...2 Innehållsförteckning...3 Förord...5 Sammanfattning...6 Inledning RISC-arkitektur - introduktion Arkitektur för feltolerant processor CPU - Instruktionspipeline Instruktioner Instruktionsuppsättning Programmering av processorn Målsättning Prestandaökande metoder Separat hoppberäkning/verifiering Forwarding ALU Metoder för feldetektering Bergerkod CRC-checksumma Assemblatorn Övervakning av multiplexrar Dubblerade funktioner Användning av metoder för feldetektering Instruktion Villkorliga/ovillkorliga hopp Villkorligt hopp Ovillkorligt hopp TRAP genererade hopp Aritmetiska operationer Läsning/skrivning till dataminnet och IO portar Läsning/skrivning till dataminne Läsning av IO portar Skrivning till IO portar Instruktionshämtning Åtgärder vid detekterat fel Implementation KRETS IF-steget ID-steget EX-steget BC-steget WB-steget IO-portar IO-port A IO-port B IO-komparator FELHANTERAREN KRETS BP-blocket IO-port C Pulsdetektorn Feleffektsanalys Resultat Slutsats Diskussion och vidare arbete
4 13 Referenser...45 Bilaga 1 Instruktioner...46 Bilaga 2 IF-steget...49 Bilaga 3 ID-steget...50 Bilaga 4 EX-steget...51 Bilaga 5 BC-steget...52 Bilaga 6 WB-steget...53 Bilaga 7 Felhanteraren...54 Bilaga 8 Skifter...55 Bilaga 9 BP-blocket...56 Bilaga 10 Assemblatorn ASRC...57 Bilaga 11 Applikation...58 Bilaga 12 Assemblerkod för styrprogrammet Bilaga 13 VHDL-kod för Krets Bilaga 14 VHDL-kod för Krets
5 Förord Denna rapport är resultatet av ett examensarbete genomfört vid SP Sveriges Provningsoch Forskningsinstitut, enheten för elektronik, sektionen för programvara (ELp) sommaren och hösten år Studenterna Andreas Söderberg och Tomas Holmgren avslutade med detta examensarbete sin civilingenjörsutbildning vid Chalmers tekniska högskola med inriktning mot elektronikkonstruktion. Examensarbetet är ett konstruktionsprojekt vilket syftar till att designa ett avancerat digitalt system som anknyter till de kurser som studenterna läst under sin utbildning. Handledaren för examensarbetet vid SP heter Johan Hedberg och examinatorn vid Chalmers Tekniska Högskola heter Peter Folkesson. Vi vill tacka vår handledare Johan Hedberg för de givande diskussioner samt stöd som givits oss under examensarbetets gång. Vi vill även tacka Peter Folkesson vid Chalmers Tekniska Högskola (inst. för datorteknik) för förbättrande idéer samt att vi har fått låna utrustning vilken möjliggjorde implementation av systemet och därmed färdigställandet av examensarbetet. Andreas Söderberg Tomas Holmgren 5
6 Sammanfattning Syftet med detta examensarbetet var att konstruera en enkanalig mikroprocessor avsedd för användning i säkerhetskritiska applikationer med krav på felsäkerhet. Eftersom processorn är enkanalig ställs endast krav på feltystnad i händelse av fel. Processorn konstruerades i VHDL och implementerades i ett färdigt målsystem FPGA labkortsystem som utlånades av Chalmers Tekniska Högskola. För att visa processorns funktionalitet konstruerades även en enkel applikation i form av ett tvåhandsmanöverdon som kunde styra en 230V anslutning. För att möjliggöra programmering av processorn utvecklades även en assemblator, i programmeringsspråket ADA. Assemblatorn översätter assemblerkod till antingen en script -fil anpassad för nerladdning av applikationsprogrammet i labsystemet eller ett VHDL-block för simulering. Resultatet av examensarbetet blev en processor som uppfyller kraven på feltolerans enligt en feleffektsanalys som genomförts. För att visa att processorimplementationen verkligen uppfyller feltoleranskraven krävs en mera grundläggande utvärdering, t ex med hjälp av felinjicering, som inte ryms inom examensarbetets omfattning. 6
7 Inledning Vid konstruktion av säkerhetskritiska programmerbara elektroniska system är en viktig del av konstruktionsarbetet att ta hänsyn till de potentiella felorsaker som systemet kommer att utsättas för då det sätts i drift. För att hantera dessa potentiella felorsaker ingår det i konstruktionen att systemet har möjlighet att övervaka sin egen funktion samt att systemet kan vidta övergripande åtgärder om systemets funktion avviker från sin specifikation. En mycket användbar metodik för implementation av övervakande funktioner är redundanta funktioner. En redundant funktion är en extra funktion vilken fyller samma syfte som den funktion som den ska övervaka. Redundans kan införas på olika systemnivåer och i olika omfattning beroende på de felorsaker som är förenade med systemet. För att ytterligare konkretisera begreppet redundans ges nedan exempel på de övergripande tillvägagångssätten (principerna) för att skapa redundans: Hårdvarumässig redundans: En elektronisk funktion (t ex processor) mångfaldigas och de olika resultaten från funktionerna jämförs för att upptäcka avvikelser. De olika funktionerna behöver inte nödvändigtvis vara implementerade på samma sätt. Mjukvarumässig redundans: Samma programvara mångfaldigas och exekveras samtidigt. Detta är ett vanligt förfarande vid hårdvarumässigt redundanta mikroprocessorsystem. Resultaten från de olika programvarorna jämförs för att upptäcka avvikelser. Programvarorna i ett sådant system brukar ha samma funktion men vara programmerade på olika sätt, annars är risken stor att ett fel i en programvara samtidigt uppträder i de övriga. Detta kallas för N-version program eller diversifierade program. Informationsmässig redundans: Samma meddelande skickas flera gånger från en sändare till en mottagare. Ett av meddelandena kan t ex skickas i form av en checksumma. Meddelandena jämförs sedan för att upptäcka avvikelser. Denna typ av redundans innefattar även informationslagring i register och minnen genom mångfaldning. Tidsmässig redundans: Hårdvara eller mjukvara mångfaldigas och utför samma operation vid olika tidpunkter. Exempel på denna typ av redundans är att lagra två (eller flera) uppsättningar av samma programvara i ett minne. Efter att första programmet är exekverat lagras resultatet och nästa program exekveras. Därefter jämförs resultaten från de båda programmen för att upptäcka avvikelser. I vissa säkerhetskritiska applikationer krävs det att styrsystemet förmår att kontrollera applikationen även i händelse av fel. För att uppfylla detta krävs minst en dubblering av den elektronik som ansvarar för de säkerhetskritiska funktionerna i styrsystemet. Beträffande maskinstyrningar finns det dock ett antal säkerhetskritiska applikationer vars styrsystem måste ha egenskapen att upptäcka fel och i så fall endast kunna försätta applikationen i ett speciellt säkerhetstillstånd. Det är idag praxis att använda sig av dubblerade system till styrsystem även till sådana applikationer. Detta innebär att styrsystemen blir överdimensionerade och dyra. Detta examensarbete syftar till att specificera och designa en enkanalig och feltolerant processorarkitektur som kan ersätta ett två-kanaligt processorbaserat system med avseende på feltolerans. Orsaker till att fel kan uppstå i en processor är såväl miljöberoende (t ex strålning och elektromagnetiska/ledningsbundna störningar/transienter) som materialberoende fel orsakade av ålder eller förslitning eller feldimensionering. Målsättningen med denna 7
8 processor är att den ska kunna upptäcka samtliga typer av enkelfel såväl transienta som permanenta. Designen grundar sig på att utnyttja pipelining för att primärt öka feltoleransen istället för prestanda samt att nyttja informationsredundans via kompilatorn. För att minimera hårdvarukostnaden nyttjas dessutom tidsredundant exekvering istället för hårdvaruredundans. 8
9 1 RISC-arkitektur - introduktion I detta avsnitt ges en mycket kortfattad introduktion till RISC-arkitekturen. En processor baserad på en RISC-arkitektur (Reduced Instruction Set Computer) är en pipelinad dator med följande egenskaper: -Den exekverar en instruktion per cykel -Har många register -Har kraftigt reducerad instruktionsuppsättning Att en processor är pipelinad innebär att dess olika funktioner är indelade i olika block med register emellan. Det vill säga att varje instruktion tar lika många klockcykler på sig att exekveras som det finns pipelinesteg. Eftersom varje pipesteg kan innehålla en unik instruktion kan processorn exekvera en instruktion per klockcykel. Arkitekturen i figur 1 har delat data- och instruktionsminne. Dataminnet accessas från WB-steget och instruktionsminnet accessas från IF-steget. Figur 1: Exempel på RISC-pipeline Exempel på instruktionsformat: [OP][DEST][SRC1][SRC2] OP = operationskod samt adresseringsmod DEST = Målregister i vilket resultatet av operationen ska lagras SRC1 = Första datafältet (vanligen en adress till registerbanken) SRC2 = Andra datafältet (adress till registerbanken eller ett tal) IF (Instruction Fetch) Steget läser instruktionen från instruktionsminnet ID (Instruction Decode) Steget avkodar instruktionen till styrsignaler och datafält I detta steg ligger registerbanken. EX (Execute) Steget exekverar operationen med datafälten från ID-steget WB (Write Back) Steget skriver resultatet från EX-steget till registerbanken, dataminnet eller IO-portarna beroende på vilken operation som exekverats. För mer information om RISC-arkitekturen se [RISC]. 1.1 Arkitektur för feltolerant processor Processorarkitekturen som konstruerades under examensarbetet är baserad på RISCarkitekturen i kapitel 1men utökad för feltolerans. Processorn är uppdelad i två separata kretsar för att begränsa felspridningsområdet och för att minska sannolikheten för sk. common-mode failures. Med separerade kretsar menas här två fristående chip med två oberoende klockor. Processorn har en ordlängd på 24 bitar. 9
10 * * * * * Figur 2 ger en översiktlig bild av processorns implementation i de båda kretsarna. De i figuren ingående blocken kommer noggrant att beskrivas längre fram i rapporten. I KRETS 1 finns själva CPU:n (se avsnitt 1.2), två stycken IO-portar (IOa, IOb) om vardera 12 IO-pinnar, en pulsräknare (PC) samt ett felhanteringsblock (FH). I KRETS 2 finns en kopia av felhanteraren från KRETS 1 (FH), ett block för bergerkodshantering (BP), en kopia av pulsräknaren från KRETS 1, samt en IO-port (IOc) vilken en av IO-portarna från KRETS 1 måste passera. %#! " # $& $# Figur 2: Processorn På grund av att båda kretsarna kan styra varsin IO-port med sina respektive felhanterare kan de båda kretsarna oberoende av varandra försätta minst en av IO-portarna i säkerhetsläge för att indikera närvaro av fel, dvs. processorn är feltyst. IO-portarna är gjorda så att även applikationen som processorn ska styra måste vara feltolerant och kunna upptäcka ej tillåtna utsignalskombinationer på de båda IO-portarna. 1.2 CPU - Instruktionspipeline CPU:n är uppbyggd med den i avsnitt 1 nämnda RISC-arkitekturen som underlag. Det som främst skiljer denna instruktionspipelinen med RISC-pipelinen är att steget BC har tillkommit. En närmare beskrivning av samtliga block ges längre fram i denna rapport. ')( ')+,-.0/ 12. Figur 3: CPU:ns instruktionspipeline Registerbanken som finns i ID-steget innehåller 32 st. register. 10
11 2 Instruktioner En instruktion till den feltoleranta processorn är uppbyggd på följande sätt: [OP] [DEST] [SRC1] [SRC2] Instruktionen avkodas i sina adresseringsmoder till följande fall REGISTER SRC1 och SRC2 innehåller adresser till registerbanken, DEST innehåller adressen till registerbanken i vilken resultatet av operationen ska lagras. IMMEDIATE SRC1 innehåller en adress till registerbanken och SRC2 är värdet från immediatefältet som (i processorn) utökas till 24 bitar beroende på signbiten (bit 12). DEST innehåller adressen till registerbanken i vilken resultatet av operationen ska lagras. EXTENDED IMMEDIATE SRC1 innehåller en adress till registerbanken och SRC2 är värdet från immediatefältet som flyttas till de tolv mest signifikanta bitarna, övriga bitar sätts till noll. DEST innehåller adressen till registerbanken i vilken resultatet av operationen ska lagras. 2.1 Instruktionsuppsättning En instruktion innehåller 59 bitar och är utformad enligt följande: [AM][OP1][OP2][PCS1][PCS2][DEST][SRC1][SRC2][IMB][INB][TAGS] AM: Adresseringsmod 2 bitar OP1: Aktuell op-kod 5 OP2: Nästa op-kod 5 PCS1: Nästa instruktionsadress 4 PCS2: Förväntad instruktionsadress vid hopp 4 DEST: Adress till destinationsregistret 5 SRC1: Adress till register 5 SRC2: Data eller adr. till reg 12 IMB: Bergerkod för immediate-fält 5 INB: Bergerkod för hela instruktionen 6 TAGS: Kanalidentitet för multiplexrar 6 Samtliga av dessa förkortningar och begrepp kommer att förtydligas senare i rapport. Processorn har följande instruktionsuppsättning. I tabell (-) = Illegal instr. OP-KOD REG IMM XIMM ADD (NOP) ADDI ADDX SUB SUBI SUBX AND CMPI CMPX ORA ORAI ORAX XOR ANDI ANDX CMP XORI XORX ADV ADVI ADVX SUV SUVI SUVX LLS LLSI LLSX LRS LRSI LRSX 11
12 01010 ALS ALSI ALSX ARS ARSI ARSX BEQ BNE RFT TRP RIO LDW LDWI LWX PUT SDW SWX PRT SFE RST - Tabell 2: Instruktionsuppsättning 2.2 Programmering av processorn Nedanstående tabell visar hur många cykler de olika instruktionerna kräver för att exekveras (dvs. hur många instruktioner av typen NOP som måste finnas i programmet efter instruktionen, undantaget branch-instruktioner) : Operation Antal cykler/op Aritmetiska operationer 1 Branch, TRP, RFT 2 RIO, LDW 5 Övriga 1 Tabell 1: Antal klockcykler per instruktion Då processorn ska programmeras måste ett visst tillvägagångssätt följas. Ett program ska vara uppbyggt på följande sätt (se bilaga 1 för en beskrivning av samtliga instruktioner): Adress Operation Kommentar 0 BEQ R0 R0 START RESET Jump to START 1 NOP TRAP handler 2 TST n RFT Return From Trap n+1 NOP n+2 TST START n+m - Program Vid reset sätts alltid programräknaren (PC) till adress 0. Där måste ett ovillkorligt hopp tas som hoppar till adress n+2 (START). Detta på grund av att processorn inte har en korrekt återhoppsadress lagrad för instruktionen RFT efter en reset. Vid användning av hoppinstruktioner: Varje, till hoppinstruktionen, efterföljande instruktion kan ha godtycklig OP-kod men instruktionen efter den ska ha samma OP-kod som den instruktion som exekveras först om hoppet tas. Se program ovan där BEQ efterföljs av instruktionen NOP och därefter 12
13 TST vilken också återfinns på måladressen (START). Om detta inte efterföljs kommer processorn att försättas i feltyst läge. Hoppvektorn refereras relativt den närmst efter hoppinstruktionen följande instruktion. Det vill säga att om hoppvektorn = 0 sätts programpekaren (PC) på instruktionen som följer hoppinstruktionen. I programmet ovan ska START bytas mot n+1 vilket ger att hoppet går till n+2. Se även nedanstående exempel: m BEQ R0 R0 1 m+1 NOP Programpekaren sätts alltid till adress (m+1)-1 = m, det vill säga att programmet är en oändlig loop. Utöver ovanstående programtekniska krav ska programmen till processorn utformas för feltolerans på samma sätt som om processorn inte var feltolerant. Nedanstående principer är exempel på några tillvägagångssätt som bör vara inkluderade i programvaran. Structured programming: Mjukvaran ska vara utformad på ett sådant sätt att den är enkel att analysera. Se även [IEC , clause B6] Software diversity: En specifikation för ett applikationsprogram är utformat i N olika varianter. Samma insignaler ges till de N programmen varefter de N uppsättningarna av utsignalerna jämförs. Se även [IEC , clause B17] (Detta kan i vissa fall göras på vissa delar av en programvara, t ex säkerhetskritiska funktioner) Well defined output control: Rimlighets plausability kontroller ska göras före och efter förändring av värdet på utgångar. Utgångarna ska styras från en väl definierad del av mjukvaran. Se även [IEC , clause B15] Plausability check of input variables: Inparametrar till funktioner/procedurer bör rimlighetskontrolleras innan de används. Se även [IEC , clause B15] Selftest using software: Speciell mjukvara kontrollerar att processorns funktioner fungerar vid start och reset. Se även [IEC , clause C.3.1 och C.3.2] Software monitoring: Programsekvensen är övervakad av programvara (som en programvaru-watch dog). Se även [IEC , clause C.9.3 och C.9.4] Instruction set test: Alla instruktioner i instruktionsuppsättningen bör testas av programvaran innan de används. Invariable memory: Programvara som genomför minnestester vid start och/eller i drift på instruktionsminnet. Se även [IEC , clause C.4] Variable memory: Programvara som genomför minnestester vid start och/eller i drift på dataminnet och registerbanken. Se även [IEC , clause C.5] Den instruktion som finns för att testa processorns förmåga att upptäcka fel (TST) ska användas med tillräckligt täta tidsintervall. Den som utformar applikationsprogrammet till den feltoleranta processorn bör ändvända sig av ovanstående metoder, samt lägga till de metoder som är relevanta för applikationen (och dess krav på feltolerans) som processorn ska styra. 13
14 Mer information om hur ett säkerhetskritiskt program ska utformas finns att läsa bla i rapporten [SP REPORT 1997:12] och i standarden [IEC 61508] (se referenslista). 3 Målsättning Målsättningen med konstruktionen av den felsäkra varianten av processorn är att processorn omedelbart ska upptäcka alla enkelfel som påverkar dess funktionalitet. Ett latent fel ska inte orsaka förlust av processorns feltolerans i kombination med ytterligare ett enkelfel. Övergripande åtgärd om fel detekteras: Om fel upptäcks görs ett försök till återhämtning, dvs. operationen repeteras en gång. Om felet kvarstår sätts processorn i feltyst läge. Processorn är utrustad med dubblerade IO-portar. Feltyst läge innebär att dessa låses till ett bestämt värde (alla utgångar sätts låga). Processorn ska dessutom vara robust i drift. För att uppnå ovanstående målsättning har följande övergripande principer använts vid konstruktionen av processorn: Processorns funktionalitet är uppdelad i två separata kretsar (chip). Alla felupptäckande mekanismer ska vara implementerade på minst två ställen i processorn (tids- eller hårdvarumässig redundans) Assemblatorn är utformad så att den kan prediktera dataflödet genom processorn samt infoga informationsmässig redundans i instruktionen. Samtliga fel indikeras på en speciell buss som genomlöper hela pipelinen. Feldetekteringsmekanismerna korrigerar respektive bit i bussen vilken initieras som om alla fel har upptäckts för varje exekverad instruktion. Möjlighet att prova samtliga felupptäckande mekanismer med en speciell instruktion vilken stimulerar dessa mekanismer att generera felsignaler. Felhanterarna ska vara utformade så att de för denna instruktion endast accepterar ett resultat på felbussen som innehåller samtliga fel. Kontroll av att samtliga piperegister uppdaterar sina värden vid exekvering. Kontrollera data som lagrats i registerbanken och instruktionsminne hårdvarumässigt med hjälp av checksummor (bergerkoder). Data lagras i dataminnet tillsammans med sin checksumma. I registerbanken lagras även skrivadressen för att hårdvarumässigt kontrollera att data lästs/skrivits från rätt adress. Kontroll av data skrivs/läses från korrekt adress i dataminnet görs i mjukvara. IO-portarna ska vara utformade så att de är dubblerade. På så sätt kan applikationen som processorn är ansluten till konstrueras så att den jämför utsignalerna, och försätts i feltyst läge om dessa inte överensstämmer. Insignalerna från de båda IO-portarna ska jämföras innan de skrivs till registerbanken. Med enkelfel menas i denna rapport: Stokastiskt fel, som kan uppstå i hårdvara såväl som i mjukvara. I denna kategori av fel inräknas också spridningsfel med gemensam orsak (Common Cause Failures, CCF) men däremot inte multippelfel av typen; flera identiska enkelfel som inträffar i olika redundanta kanaler vid samma tidpunkt (Common Mode Failures, CMF). Inte heller ingår multippelfel av typen; flera olika enkelfel som inträffar vid samma tidpunkt (Different Mode Failures, DFM). 14
15 Följande fel upptäcks av processorn Permanenta enkelfel Analyseras med en integrerad testsekvens i programvaran. Åtgärd om fel upptäcks: Möjlighet att använda speciell instruktion för att försätta processorn i feltyst läge. Transienta enkelfel Störningar i hårdvaran/fel i programvara analyseras med funktioner implementerade i hårdvaran. Åtgärd om fel upptäcks: Operationen repeteras en gång, om felet kvarstår sätts systemet i feltyst läge. Om ett fel upptäcks registreras detta på en speciell databuss (failurebus) som är ansluten till felhanteraren (FH). Felhanteraren vidtar sedan åtgärd beroende på vilken typ av fel som anges på failurebus. 4 Prestandaökande metoder För att processorn inte ska förlora allt för mycket prestanda beroende på de feltoleranta egenskaperna har vissa konstruktionsmässiga åtgärder vidtagits. 4.1 Separat hoppberäkning/verifiering Det naturliga tillvägagångssättet att beräkna den nya adressen vid hopp (även verifiera villkoret för hopp) är att använda sig av ALU:n (Arithmeic Logic Unit) som finns i EXsteget (se figur 1). Detta sparar hårdvara eftersom ytterligare en komparator samt adderare annars måste finnas med i konstruktionen. Problemet med detta tillvägagångssätt är att detta tar 3 klockcykler att genomföra, och de instruktioner som läses in i pipelinen under två av klockcyklerna måste förkastas om hoppet genomförs. Förkastade instruktioner innebär i sin tur att det blir tomma luckor ( stall s ) i pipelinen som inte uträttar något arbete. I den feltoleranta processorarkitekturen har denna beräkning lagts i ID-steget (se bilaga 3, BRANCH LOGIC) för att spara en klockcykel vid hopp och därmed minska antalet stall s till en. 4.2 Forwarding Då en instruktion måste ha data från en tidigare exekverad instruktion som fortfarande ligger kvar i pipelinen uppstår problem med stall s. Betrakta följande exempel: ADD R1 R2 R3 SUB R4 R1 R5 Då instruktionen SUB ska läsa registerbanken har inte den tidigare instruktionen ADD exekverats färdigt genom pipelinen och har därför inte hunnit skriva resultatet i R1 (Detta kallas för RAW- (Read After Write) fel). Därför måste SUB vänta tills ADD gått igenom pipelinen, vilket innebär stall s. De flesta instruktionerna har en destinationsadress till registerbanken som följer instruktionen genom pipelinen. Genom att jämföra läsadresserna för SRC1 och SRC2 med destinationsadresserna för samtliga instruktioner längre fram i pipelinen går det att upptäcka om liknande problem har uppstått som i ovanstående exempel. Med forwarding menas att i så fall läsa tillbaka resultatet från den instruktionen direkt ifrån pipelinen och därmed inte behöva vänta på att resultatet ska skrivas i registerbanken (se bilaga 3). Detta fungerar inte för alla instruktioner, t ex läsning från IO-portar och dataminne. 15
16 4.3 ALU Adderaren i en ALU används ofta under exekvering av instruktioner. Om adderaren är långsam kan det påverka processorns totala prestanda märkbart. I den feltoleranta processorn har därför adderaren utformats enligt principen carry look ahead (se bilaga 4). I en vanlig adderare är inte beräkningen klar förrän carry-biten ripplat genom alla heladdrare som den är uppbyggd av. Med carry-look ahead minskas tiden för carryripplet. 5 Metoder för feldetektering 5.1 Bergerkod En bergerkod är en slags checksumma som beräknas genom att räkna antal ettor eller nollor i ett binärt tal. Syftet med bergerkoder är att om två tal finns tillgängliga med tillhörande bergerkoder är det möjligt att förutsäga bergerkoden för resultatet av en aritmetisk operation utan att utföra den aritmetiska operationen (se avsnitt 8.2.1, BPblocket). Det vill säga att det är möjligt att övervaka ALU:n i processorn med begerkoder. I processorn lagras alla tal tillsammans med sina bergerkoder (förutom vid TRAP). Eftersom bergerkoden också fungerar som en checksumma används bergerkoder för att kontrollera att de data som är lagrat i minne (registerbank, instruktionsminne och dataminne) fortfarande har samma bergerkod när det läses. Vid läsning av IO-portar skapas en bergerkod av resultatet som sedan skrivs tillbaka tillsammans med resultatet. Bergerkoder kan upptäcka enkelfel samt multipelfel i datamängder om multipelfelen är riktade åt samma håll det vill säga att alla bitar i multipelfelet fallerar till samma tal 1 eller 0. Exempel: Korrekt data Inkorrekt data Detekterat Feltyp Ja Enkelfel Nej Oriktat multipelfel Ja Likriktat multipelfel 5.2 CRC-checksumma CRC (Cyclic Redundancy Check) är en sorts checksumma beräkning med mycket hög feltäckningsgrad. CRC checksumman beräknas med en binär division mellan data och ett tal (sk. polynom). Den rest som blir över efter divisionen är CRC-checksumman (se avsnitt 8.1.1). Divisionen som genomförs kallas även för modulo-2 division vilket innebär följande: Vid en vanlig heltalsdivision används högsta möjliga faktor vilken multipliceras med divisorn varefter produkten subtraheras bort från talet som ska divideras. Kvar blir en rest. Vid binär modulo-2 division ersätts subtraktionen med en XOR-operation mellan divisorn och resten. Genom att skifta datat lika många bitar åt vänster som polynomets längd-1fås alltid en sista rest (CRC) med samma bitlängd efter datat. Vid skift åt vänster fås lika många nollor till höger om datat som den förväntade CRC:ns längd. Om istället nollorna ersätts av en tidigare genererad CRC och divisionen genomförs kommer alltid resten bli noll om datat är samma som då CRC:n genererades. 16
17 På grund av att CRC-algoritmen utgörs av skiftningar och XOR-operationer är den lämplig att implementera i hårdvara. I processorn används CRC checksummor för att beräkna signaturer av programräknaren. Varje instruktion innehåller två programräknarsignaturer, en för nästa instruktion och en för möjlig nästa instruktion om hopp tages. 5.3 Assemblatorn Assemblatorn förutsäger två stycken programräknarsignaturer, en för nästa instruktion (PCS1) och en för nästa instruktion om hopp tagits (PCS2). Assemblatorn lägger även in nästa operationskod (NOP) i instruktionen. Bergerkoden till immediate-fältet beräknas av assemblatorn som även tar hänsyn till om immediate-fältet ska utökas med teckenbiten. Beroende på vilken instruktion som behandlas av assemblatorn, kan assemblatorn förutsäga vissa datavägar genom processorn. Assemblatorn anger datavägen i instruktionen med en TAG (se avsnitt 5.4) som sedan används för att verifiera att multiplexarna ställt sig rätt. Slutligen beräknas en bergerkod till hela instruktionen för att säkerställa att instruktionen lästs rätt från instruktionsminnet. 5.4 Övervakning av multiplexrar Vissa multiplexrar övervakas på så sätt att TAGs (se avsnitt 8.1.2) läggs till respektive dataingång. Denna TAG är unik för varje dataingång till multiplexern vilket medför att det går att se på utgången hur multiplexern adresserats. Assemblatorn förutsäger hur multiplexern ska adresseras beroende på vilken instruktion som exekveras och lägger till denna information till instruktionskoden. En komparator jämför sedan den TAG som ges på multiplexerns utgång med informationen från assemblatorn. Om multiplexern adresserats felaktigt kan detta upptäckas. Det går inte att förutsäga datavägen genom forwarding-blocket med assemblatorn. Varje TAG på dataväg till forwarding-blocket läggs till i respektive pipelinesteg. Identiteterna kontolleras sedan genom att dubblera komperatorena som jämför adresserna som avgör om datat ska forwardas. En uppsättning komperatorer styr multiplexrarna och dubbletterna förutsäger vilken identitet som ska ha forwardats. 5.5 Dubblerade funktioner Felhanteraren, en pulsräknarkrets samt IO-portarna är dubblerade och har en uppsättning i varje krets. Detta för att kretsarna ska kunna övervaka varandra och ha möjlighet att sätta åtminstone en av IO-portarna i feltyst läge. Felhanterarna kontrollerar inte varandras funktion. Istället antas att sannolikheten för att ett latent fel i en av felhanterarna ska åtföljas av ett fel i den andra felhanteraren vara mycket låg eftersom de är lokaliserade i olika kretsar. Funktionen hos IO-portarna kan kontrolleras av mjukvara och funktionen hos pulsräknarna (ska) kontrolleras av en extern watch-dog krets. 17
18 6 Användning av metoder för feldetektering 6.1 Instruktion Varje instruktion innehåller en bergerkod för att kontrollera att instruktionen lagrats/hämtats korrekt från instruktionsminnet. Varje instruktion innehåller bla information om -Aktuell op-kod -Efterföljande op-kod -Efterföljande CRC signatur av PC -Möjlig efterföljande CRC signatur av PC vid taget hopp -Bergerkod för immediate-fält -Multiplexeridentitet (TAG) för kontroll av dataflöde -Bergerkod för hela instruktionen I nedanstående avsnitt ( ) beskrivs översiktligt hur denna information används tillsammans med de övriga metoderna för feldetektering. 6.2 Villkorliga/ovillkorliga hopp Redundans införs genom att en PC-signatur beräknas dels av assemblatorn och dels av processorn. Assemblatorn lagrar i varje instruktionskod den förväntade op-koden och tillhörande PC-signatur för nästa instruktionsadress samt PC-signatur för nästa instruktionsadress vid taget hopp Villkorligt hopp Bergerkod används för att verifiera att komparatorn i branchmodulen fungerar korrekt. Hoppadressen kontrolleras med hjälp av den förväntade PC-signaturen som kompilatorn beräknat Ovillkorligt hopp Ovillkorliga hopp verifieras endast genom kontroll av hoppets måladress (PCS) TRAP genererade hopp Kompilatorn placerar TRAP-rutinen vid en känd startadress i instruktionsminnet. Mjukvarugenererad TRAP Aktuell PC lagras i register R31 (låses för skrivning) samt PC:ns signatur (PCS) i en buffert i IF-steget, TRAP-rutinens startadress flyttas till PC. Vid återhopp kan sedan innehållet i bufferten kontrolleras. Hårdvarugenererad TRAP Den instruktion som ligger först i pipen byts ut mot en mjukvarutrap och behandlas sedan på samma sätt som mjukvarugenererad TRAP. 6.3 Aritmetiska operationer All data i registerbanken och dataminnet lagras tillsammans med tillhörande bergerkod. Vid en aritmetisk operation används bergerkoderna till operanderna för att förutsäga vad resultatet av operationen kommer att få för bergerkod. Den beräknade bergerkoden 18
19 jämförs sedan med en bergerkod som är genererad av resultatet. Bergerkoderna används även för att kontrollera komparatorn i branch-hanteraren i ID-steget. 6.4 Läsning/skrivning till dataminnet och IO portar Figur 1.2 beskriver hur IO-portarna och dataminnet är anslutna till processorn Läsning/skrivning till dataminne All data som lagras i dataminnet/registerbanken skyddas av bergerkoder vilket gör att fel i datat upptäcks när det ska användas. Adresseringsfel i dataminnet upptäcks av minnestester implementerade i mjukvaran Läsning av IO portar Processorn har två stycken identiska IO-portar samt en transparent IO-port. IO-portarna har vardera 12 IO-signaler. Alla IO-signaler i IO-portarna kan konfigureras som ingång eller utgång. Om en IO-signal är konfigurerad som en ingång kan man även ange en prioritet på den. När ingångarna läses sammanfogas ingångarna från två IO-portar. Sammanfogningen sker på två sätt, antingen ska signalerna vara inverterade eller lika beroende på vilken prioritet som angivits. Resultatet av läsningen lagras i de 12 minst signifikanta bitarna och i de 12 mest signifikanta bitarna lagras statusbitar som anger om signalparen överensstämmer med den angivna prioriteten Skrivning till IO portar Vid skrivning till IO-portarna skrivs samma värde till de IO-signaler som är definierade som utgångar. Felsäkerheten från processorns sida ligger i att de tre IO-portarna var för sig kan tvingas till ett feltyst läge om ett fel i processorn upptäcks. 6.5 Instruktionshämtning För att en instruktion ska få hämtas från instruktionsminnet måste dess adress (PC) överensstämma med den som lagrats från föregående instruktion (PC signatur). Undantag görs i händelse av TRAP instruktion. 7 Åtgärder vid detekterat fel Om fel upptäcks görs ett försök till återhämtning, dvs. operationen repeteras en gång. Om felet kvarstår sätts processorn i feltyst läge. Feltyst läge innebär att alla utgångar på IOportarna sätts låga av felhanterarna. 8 Implementation Processorn är implementerad med hjälp av VHDL. Nedan följer den tekniska och funktionella beskrivningen av processorns olika block, samt dess mellanliggande signaler och bussar. Beskrivningen utgörs av blockdiagram för de olika stegen, dessa blockdiagram stämmer inte nödvändigtvis överens med den RTL-fil som syntesverktyget skapar vid syntes utan syftar bara till att ge en enkel och övergripande inblick i systemets olika funktioner och dess implementation. Beteckningar i blockdiagrammen: Då antal signaler i en buss måste förtydligas görs detta med följande beteckning i blockdiagrammen: bn:m där n högsta bitnummret i bussen och m lägsta. Ex. b4:0 är en 5-bitars buss med mest signifikanta biten 4. 19
20 Om inget anges har bussen samma bredd som den hade senast den betecknades (speciellt vid förgreningar). Varje beskrivning nedan inleds med en översiktlig beskrivning av blockets funktion följt av en beskrivning av vilka metoder för feldetektering som blocket använder. Efter detta kommer en lite fördjupad teknisk beskrivning av blockets implemention som läses tillsammans med respektive blockdiagramm i någon av bilagorna 2 9. Den tekniska beskrivningen syftar till att ge förståelse av VHDL-koden i bilaga 13 och 14. Vissa delar av processorn beskrivs i den tekniska beskrivningen men är inte utritade i blockdiagrammen. Detta för att block-diagrammen främst syftar till att illustrera dataflödet genom processorn och därför inte vara allt för detaljerade. Dessa delar är istället beskrivna i texten. Processorns uppbyggnad av VHDL-komponenter beskrivs av VHDL-koderna KRETS1 och KRET2 (bilaga 13 respektive 14). Själva CPU:ns uppbyggnad ges av VHDL-koden CPU (bilaga 13). Varje ingående VHDL-block är refererat från den tekniska beskrivningen nedan. 8.1 KRETS IF-steget FUNKTION I detta steg hämtas instruktionen från minnet. Steget infogar även avbrottsinstruktionen TRAP vid externt avbrott. Ett avbrott innebär att en speciell TRAP-hanterare exekveras. Denna TRAP-hanterare har en fördefinierad startadress i instruktionsminnet. Programmet återgår till den programadress där avbrottet detekterats då instruktionen RFT (Return From Trap) exekveras. För varje instruktion som hämtas lagras programräknaren (PC), nästkommande instruktion (NOP) samt en signatur (PCS1) för nästkommande PC för normal exekvering och vid taget hopp (PCS2) i varsin stack. Stackarna används för att senare kunna köra om en instruktion om ett fel upptäcks i processorn samt för att kunna infoga en TRAPinstruktion i instruktionskedjan. Även NOP, PCS1 och PCS2 i den hämtade instruktionen lagras i respektive register. FELDETEKTERING När instruktionen hämtas beräknas en CRC-checksuma för den aktuella adressen (PC), denna checksumma jämförs sedan med den som lagrats från föregående instruktion PCS1 (eller PCS2 om hopp taget). PCS1 och PCS2 genereras av assemblatorn. Undantag görs i händelse av TRAP. Vid händelse av att den hämtade instruktionen är RFT jämförs PCS2 med ett särskilt register som skrevs vid en tidigare TRAP-instruktion. Detta register innehåller signaturen för återhoppsadressen från TRAP-hanteraren. Den hämtade operationskoden (OP) jämförs med den som lagrades i föregående instruktion (NOP). En berger-räknare går igenom hela instruktionen varefter resultatet jämförs med den av assemblatorn beräknade bergerkoden INB. Om INB inte överensstämmer med den framräknade bergerkoden för instruktionen sätts felsignalen im_failure hög. Om villkoren för programräknarsignaturen (PCS) eller för nästkommande instruktion (NOP) sätts felsignalen instr_failure hög. 20
21 TEKNISK BESKRIVNING Se bilaga 2 LÄSNING AV INSTRUKTION Multiplexern M0 styrs av signalen branch_taken och väljer om PC-registret ska laddas med NEXT_PC som kommer från ID-steget eller datat som finns lagrat i vippan D0. D0 innehåller adressen till den närmast efterföljande instruktionen i instruktionsminnet, denna adress är framräknad av adderaren A0. Multiplexern M1 styrs av signalen RETRY och väljer om PC:n ska hämtas ifrån stacken PC_STACK vid omkörning av instruktioner. Det från instruktionsminnet upplästa datat kommer på bussen ROM_DATA vilken är ansluten till en bergerkodsgenerator samt till multiplexern M2. Den framräknade bergerkoden jämförs i komparatorn C0 med INB som återfinns på bussen ROM_DATA. Om dessa inte är lika sätts felsignalen instr_failure hög. PC:n (XPC) är ansluten till 5 CRC-generatorer som genererar en 4 bitars CRC-kod för PC:n. Resultatet av CRC-beräkningen jämförs sedan i komparatorn C3 med PCS1 (genom D8). Om dessa inte är lika sätts signalen im_failure hög. Polynomet som används för CRC-genereringen är: 27 (b11011). Polynomet är inte valt av någon speciell orsak och användning avrekommenderas. Istället bör ett primtal användas som polynom, detta för att CRC-genereringen ska upptäcka fler fel. Varje instruktion (OP) jämförs med föregående instruktion (NOP, vippa D7) i komparatorn C2 (genom M3). Om OP inte överensstämmer med NOP kommer signalen instr_failure att sättas hög. De av assemlatorn förutsagda multiplexeridentiteterna (TAG:s) ges på bussarna wb_tag (2 bitar bred) och imm_ximm_tag (4 bitar bred). VID HOPP En hoppinstruktion kräver två klockcykler för att exekveras. I första klockcykeln ska hoppinstruktionen hämtas från IM i IF-steget och i den andra klockcykeln ska villkoret för hoppet verifieras i ID-steget. Om hoppet tas (det vill säga att villkoret för hoppet uppfylls) sätts signalen branch_taken från ID-steget samtidigt som hoppets nya instruktionsadress beräknas och ges tillbaka på bussen NEXT_PC. Den instruktion som hämtas till IF-steget under den andra klockcykeln (så kallad delay-slot ) kan väljas godtyckligt. Signalen branch_taken ställer om multiplexern M0 (och M4) så att nästa instruktion läses från den framräknade hoppadressen. M4 ställer om sig så att XPC:s CRCchecksumma istället jämförs med PCS2, precis som ovan sätts signalen im_failure hög om dessa inte är lika. Instruktionen efter delay-slot :en ska ha samma OP som den instruktion som läses om hoppet tas. Annars sätts instr_failure hög. Orsaken till det är NOP-testet. VID TRAP En TRAP är ett avbrott och behandlas av processorn som ett ovillkorligt hopp med förutbestämd destinationsadress. De instruktioner som direkt följer denna destinationsadress kallas för TRAP-hanterare och ska avslutas med instruktionen RFT. Det finns två typer av TRAP-funktioner, mjukvarugenererat TRAP och hårdvarugenererat TRAP. Komparatorn C1 kontrollerar om den lästa instruktionen är TRAP. I så fall ges signal till D3 och D4 som lagrar NOP och PCS (NOP_trap och PCS_trap). 21
22 Vid ett hårdvarugenererat TRAP sätts vippan D1 om inte den samtidigt upplästa instruktionen är en hoppinstruktion eller om den upplästa instruktionen befinner sig i en sk. delay-slot. Vippan D1 och D2 genererar pulserna trap och ins_nop till som infogar en TRAP- följt av en NOP-instruktion enligt figur 4. Signalen busy förblir hög tills TRAP-hanteraren är klar och den hårdvarugenererade TRAP-signalen återigen blir låg. Detta innebär att processorn inte tar emot ytterligare en TRAP innan traphanteraren är klar. Både vid hårdvarugenererad- och vanlig TRAP sätts vippan D15 TRAP_BUSY vilken används i ID-steget för att kontrollera att RFT inte exekveras utanför TRAPhanteraren. För att få detta beteende förhindras även uppräkning av programräknaren under en cykel vid trap. Figur 4:. Timingdiagram för infogning av TRAP VID RFT (Return From Trap) Denna instruktion avslutar TRAP-hanteraren. Komparatorn C1 kontrollerar om den lästa instruktionen är RFT. I så fall sätts en signal vilken sätter vippan D5 som ger signalen rft_fin. När både rft_fin blir hög och HW_TRAP blir låg nollställs D1 (se VID TRAP). Signalen ställer också om multiplexrarna M3 och M6 vilket innebär att PCS samt NOP testerna utförs på det data som finns lagrat i D3 och D4 (NOP_trap och PCS_trap) istället för D7 och D9. VID RETRY IF-steget har tre stycken FIFO-register (First In First Out) PC_stack, NOP_stack och PCS_stack. Dessa register lagrar samma PC, NOP och PCS för varje uppläst instruktion, som ges till ID-steget. Räknaren PIPE_counter räknar i intervallet 0 5 styr vilken position i registren som data ska lagras. Den position (räknarens aktuella värde) som data lagras på motsvarar den instruktion som finns i WB-steget. Signalen RETRY ställer om multiplexrarna M1, M3 och M5 så att: M1: XPC <= PC_stack M3: NOP <= NOP_stack M5: PCS <= PCS_stack Detta bara för att inte PCS- samt NOP-testerna ska generera felsignalerna im_failure och instr_failure vid återkörning av en instruktion. RETRY sätter även signalen TRAP_RETRY (vippa D16) vilken möjliggör omkörning av instruktionen RFT. 22
23 FAILURE BUS Denna buss genomlöper hela pipelinen och innehåller samtliga felsignaler som finns i systemet då den når WB-steget. I IF-steget ges bit 0 och bit 1 av felsignalerna instr_failure och im_failure. im_failure sätts hög om PCS-testet fallerar. instr_failure sätts hög om NOP-testet fallerar eller om den genererade bergerkoden för instruktionen ej överensstämmer med INB. Vid reset ettställs alla bitar utom b0 och b1 i FAILURE_BUS som vidarebefordras till ID-steget via vippan D14. De övriga vipporna D6-D12 utgör stegets register, och vidarebefordrar data till ID-steget. Vippan D13 ger en av läsadresserna (ADDR2) till registerbanken i ID-steget. Orsaken till att den är placerad i IF-steget beror på syntesverktyget som inte kunde skapa ett block- RAM om inte samtliga adressbussar kom från register. Beroende på adresseringsmoden (AM) sätts ADDR2 till antingen dest (AM = 00 : mux_dest) eller de 5 lägsta bitarna i SRC2 (AM!= 00 : mux_src2) av M7. Se den tekniska beskrivningen av ID-steget för mer information om adresseringsmoder. Om processorn försätts i feltyst läge förhindras uppräkningen av programräknaren i IFsteget av två signaler (safe och safe2). Detta block är konstruerat med följande VHDL-beskrivningar (bilaga 13; KRETS 1), IF_stage Port map fil för IF-steget samt pipelineregister IM Läser data från instuktionsminne, genomför samtliga tester i detta steg PC_COUNTER Ökar programäknaren PC_MUX Väljer mellan programräknare genererad vid taget hopp eller den från PC_COUNTER ID-steget FUNKTION Detta steg avkodar resultatet av IF-steget till datafält och styrsignaler. Steget består främst av fyra block: Registerbanken, branchblocket, IMM_XIMM blocket, forwarding blocket samt decode-blocket. Registerbanken innehåller 31 st. register som alla kan läsas eller skrivas. Alla data (med undantag från TRAP-exekvering) lagras i registerbanken tillsammans med sina bergerkoder. I de 5 mest signifikanta bitarna lagras den adress som data är avsedd att skrivas till. Branchblocket utvärderar villkoren för hopp samt beräknar den nya adressen till instruktionsminnet. Branchblocket beräknar även den nya adressen för ovillkorliga hopp (RESET, TRAP, RFT). DECODE-blocket avkodar den inkommande operationskoden till olika styrsignaler till de övriga blocken i systemet. IMM_XIMM-blocket avgör beroende på adresseringsmoden om src2 är en adress som ska läsas i registerbanken eller om src2 i sig utgör data som ska användas i senare beräkningar. 23
24 Forwarding-blocket kontrollerar om någon instruktion längre fram i pipelinen har samma måladress som någon av src1 eller src2. I så fall läses det data som respektive måladress motsvarar direkt ifrån piperegistret. FELDETEKTERING IMM_XIMM-blocket upptäcker fel adresseringsmoden samt ifall instruktionerna TRAP och RFT har ett felaktigt register angivet i dest. Om ett fel upptäcks sätts felsignalen addr-failure hög. I detta block sätts även TAGs (dvs kanalidentitet för multiplexrar) för respektive adresseringsmod eller om det är en TRAP. Dessa TAGs jämförs sedan i ett mindre block som heter src2_mux med TAGs som genererats av assemblatorn. Om fel upptäcks ges SRC2 en felaktig bergerkod och signalen imm_ximm_failure sätts hög. DECODE blocket upptäcker om det fått en otillåten instruktion och sätter i så fall felsignalen decode_failure hög. Branch blocket upptäcker om det fått en felaktig kombination av insignaler, samt om instruktionen RFT exekveras felaktigt. Om fel upptäcks sätter blocket felsignalen branch_failure hög. Beräkningen av hoppets måladress i instruktionsminnet kontrolleras i IF steget och jämförelsen kontrolleras senare med hjälp av bergerkoder i EX-steget samt i BP-steget. Forwardingblocket kontrollerar att rätt data läses från piperegistren med hjälp av TAGs som hårdvarumässigt läggs till bussarna som är anslutna mellan forwardingblocket och motsvarande register. TEKNSK BESKRIVNING Se bilaga 3 DECODE-blocket Detta block har operationskoden som insignal och utifrån den sätter blocket en styrbuss CTRL enligt: CTRL (bit) Flagga 0 Branch flag 1 Trap flag 2 Return from trap flag 3 Används ej 4 Används ej 5 Forward not allowed flag 6 Disble reg_file test flag 7 TST instruktion flag Tabell 2: Innebörd av bitarna i CTRL-bussen 24
25 Decode-blocket sätter dessa flaggor enligt följande tabell: OP B7 B6 B5 B4 B3 B2 B1 B0 BEQ BNE RFT TRP RIO LDW PUT SW PRT SFE TST RST OTHERS Tabell 3: Bitarna i CTRL-bussen för olika instruktioner Om en odefinierad instruktion eller instruktionen TST ges till decode-blocket kommer signalen decode_failure att sättas hög. IMM/XIMM-blocket Detta block avkodar SRC2 med avseende på instruktionens adresseringsmod i följande tre moder: Register, immediate och extended immediate. Vilken som används bestäms av följande: ADDR_MODE = 00 - Register = 01 - Immediate = 10 - Extended Immediate = 11 - Inte använd Adresseringsmoden styr multiplexern M3 som väljer en av tre bussar till XDATA2 (29b). Vid register-mode (REG) ansluts XDATA2 till registerbankens ena databuss (reg_data2). Vid immediate-mode (IMM) ges de första 12 bitarna av SRC2. Den tolfte biten (teckenbiten) bestämmer om b13-b24 är endast ettor (sign extended) eller endast nollor. Bitarna b25-b29 är bergerkoden för talet. Om CTRL-bussens b1 (TRAP) eller b2 (RFT) är höga kontrollerar komparatorn C5 att data som ligger på bussen DESTin är B (register 31) annars sätts signalen addr_failure. Vid extended immediate-mode är de 12 första bitarna alltid nollor och de efterföljande 12 bitarna SRC2. De sista 5 bitarna är bergerkoden. Multiplexern M4 bestämmer om bussen DDEST ska få data från registerbanken eller innehålla PC:n beroende på b0 i bussen CTRL (om instruktionen är en branch). Multiplexern M5 bestämmer om bussen DATA2 ska vara XDATA2 (se ovan) eller DDEST beroende på b0, b1 och b2 i bussen CTRL (om instruktionen är en TRAP). Multiplexrarna M3-M5 övervakas av så kallade multiplexeridentiteter (TAGs) dessa är inte utritade i beskrivningen. Testet syftar till att kontrollera dataflödet genom multiplexrarna och följer principen som visas nedan i figur 5. 25
26 Figur 5: Princip för övervakning av dataflöde Identiteterna läggs till bussarna i IMM_XIM -steget och kontrollen görs i blocket SRC2_MUX. Skillnaden från figur 5 är att assemblatorn också har förutsagt identiteten som jämförs. Alltså används två komparatorer och två multiplexrar. Identiteterna från assemblatorn läses från bussen imm_xim_tag som kommer från IF-steget. Om fel upptäcks i kontrollen sätts felsignalen imm_ximm_failure hög samt att data (DATA2) förändras så att det har felaktig bergerkod. REGISTERBANKEN Registerbanken består av två två-ports RAM-minnen (BM1 och BM2) med vardera 32x34 bitar. Orsaken till detta är att ett två-ports RAM-minne kan läsa respektive skriva från/till en adress per klockcykel. Genom att använd två st. sådana RAM-minnen kan två adresser läsas och en skrivas per klockcykel. Varje klockcykel skrivs data WRITE_DATA till adressen WRITE_ADDR till båda RAM-blocken. De 5 högsta bitarna i det skrivna data innehåller WRITE_ADDR. Skrivning av registerbanken sker på negativ flank medan läsning sker på positiv flank. Data läses sedan från respektive RAM-block med adresserna src1_addr och src2_addr som ger data på bussarna DATA1 och DATA2. Vid läsning jämförs läsadressen med de 5 högsta bitarna i det lästa data, om dessa inte överensstämmer sätts felsignalen rbank_failure hög. Denna kontroll genomförs inte för de instruktioner som sätter bit 6 i bussen CTRL hög. Detta test är inte utritat i beskrivningen av ID-steget. src2_addr utgörs av de första 5 bitarna i SRC2 och kommer från IF-steget (ADDR2). Detta på grund av att det måste sitta register på samtliga adressbussar till RAM-blocken så att det syntesverktyg som används ska implementera minnena som riktiga RAM-block i FPGA:n (och inte som enskilda vippor för varje bit). Se även teknisk beskrivning av IFsteget. Insignalerna check och extra_check förhindrar oberoende av varandra skrivning till registerbanken. Om någon av signalerna blir hög blir write_enable låg och ingen skrivning av minnet kan förekomma. extra_check är inte utritad i beskrivningen av IDsteget. Data som lagras i registerbanken är alltså organiserat på följande sätt: b34-b30 Adressen som data avsågs skrivas till b29-b35 Bergerkoden för lagrat data b24-b00 Data BRANCH-blocket Detta block beräknar hoppvektorn (NEXT_PC) samt verifierar hoppvillkor. Komparatorn C1 kontrollerar om instruktionen är ett hopp och ger 4 styrsignaler om den är ett hopp enligt nedanstående tabell, 26
27 Instruktion Hopp taget Hopp ej taget NEXT_PC BEQ/BNE M0-0 M1-0 M2-0 M0 0 M1-1 M2-0 Hopp taget: PC + XDATA2 Hopp ej taget: Branch_taken - 1 TRAP M0 0 M1-0 M2-1 Branch_taken - 1 Branch_failure - 0 RFT M0 1 M1-0 M2-0 Branch_taken - 0 M0-0 M1-1 M2-0 Branch_taken - 0 Branch_failure - 1 M0-0 M1-1 M2-0 Branch_taken - 0 Branch_taken - 1 RESET Branch_taken - 1 Hoppet tas alltid 0 Tabell 4: signaler vid olika hoppinstruktioner PC Hopp taget: XDATA2 Hopp ej taget: PC Hopp taget: DDEST Hopp ej taget: PC BEQ/BNE: Komparatorn C2 är ansluten till multiplexern M8, och jämför bussarna DDEST och DATA1. Om dessa är lika/olika sätts NEXT_PC enligt tabell 4. TRAP: Komparatorn C4 kontrollerar att data i XDATA2 är startadressen till TRAPhanteraren (h01). XDATA2 är här IMM-fältet (SRC2). Om annat data ges i XDATA2 sätts branch_failure hög. RFT: NEXT_PC finns lagrad i registerbanken (R31) för RFT och ges i DDEST. Om instruktionen RFT fås och trap_busy inte är hög kommer branch_filure att sättas hög. RESET: Påverkar inga multiplexrar utan nollställer endast NEXT_PC. FORWARDING-blocket Detta block jämför den destinationsadress som instruktionen i ID-steget har med de instruktioner som finns i EX- respektive BP-stegen. Detta görs med komparatorerna C6- C10 och C11-C15. Bussarna som går till komparatorerna kallas för ALU_ADDR, ALU_ADDR2 och BP_ADDR. Om likhet fins med någon av bussarna src1_addr eller src2_addr kommer DATA1 eller DATA2 att bytas ut mot respektive ALU_DATA, ALU_DATA2 eller BP_DATA. Detta sker då genom multiplexrarna M6 eller M7. Datakonverterarna (CONV) illustrerar att multiplexrarna adresseras av resultatet från komparatorerna. Orsaken till att data forwardas tillbaka till ID-steget är att annars måste data lagras i registerbanken innan det kan användas av någon efterföljande instruktion. Detta skulle innebära flera cyklers fördröjning för många instruktioner. Forwarding-multiplexrarna är övervakade av multiplexeridentiteter (TAGs) enligt figur 5. Identiteterna läggs till busarna i de ställen i pipen där de börjar, men förutsägs inte av assemblatorn. Detta är inte inritat i beskrivningen av ID-steget. Om fel upptäcks sätts signalen forw_failure hög. De övriga vipporna D6-D12 utgör stegets register, och vidarebefordrar data till EX-steget samt återkopplar data (NEXT_PC, branch_taken) till IF-steget. 27
28 FAILURE BUS Följande bitar sätts i failure_bus av ID-steget: B2 addr_failure and B2(IF) B3 branch_failure and B3(IF) B4 decode_failure and B4(IF) B5 branch_taken and B5(IF) B10 imm_ximm_failure and B10(IF) B11 forw_failure and B11(IF) B12 rbank_failure and not CTRL(6) and B11(IF) Detta block är konstruerat med följande VHDL-beskrivningar (bilaga 13; KRETS 1), READ_REG Port map fil för ID-steget samt pipelineregister DECODE Genererar styrsignaler beroende på inkommande instruktion IMM_XIMM Avkodar SRC2 map adresseringsmoden REG_BANK RAM-minne med register FORWARD Hanterar forwarding SRC2_MUX Väljer DATA2/DDEST beroende på instruktion MUX_SRC1 Lägger till en bit på RDEST EX-steget FUNKTION Detta steg innehåller främst en ALU som kan beräkna de vanligaste aritmetiska operationerna med datafälten (data1, data2) som avkodades från SRC1 och SRC2 i IDsteget. EX-steget innehåller även en Barrel-shifter. FELDETEKTERING Vid en operation med ALU:n/shiftern genereras även en ny bergerkod som är specifik för den aktuella operationen. Denna bergerkod adderas sedan till resultatet av operationen. Samtidigt förutsägs resultatets bergerkod med avseende på de båda datafältens bergerkoder, operationen samt viss information från ALU:n i ett annat block (BP). Om inte den förutsagda bergerkoden sedan överensstämmer med den framräknade sätts felsignalen berger_failure1 hög. TEKNISK BESKRIVNING Se bilaga 4 Förutom att exekvera instruktionerna så kontrollerar EX-steget även att branchjämförelsen i ID-stegt utförts rätt. Detta sker genom att ta XOR mellan operanderna och se om resultatet är lika med noll. Om BEQ och resultatet är noll ska hoppet tas och B_OK sätts hög. Motsvarande om BNE och resultatet skilt från noll. Även vid de ovillkorliga hoppen TRAP och RFT sätts B_OK hög. B_OK jämförs sedan med branch_taken från ID-steget som kommer på failurebus(5) och failurebus(5) går hög ut från EX-steget om de inte är lika. Denna logik sitter i komparatorn C0 och det logiska grindnätet efter den. Addition/Subtraktion Vid addition och subtraktion används en carry-look-ahead adderare som vid subtraktion får en etta på carry-in och den andra operanden inverterad, s.k. 2-komplements subtraktion. Vitsen med att använda en carry-look-ahead adderare istället för en vanlig ripple-carry adderare är att minska tidsfördröjningen. Detta görs genom att för varje bitpar finns ett generateblock(g) och ett propagateblock(p). Vid generate vet man att det kommer att genereras en carry och vid propagate kommer carry-ut vara samma som carry-in. Värsta fallet för en ripple-carry är alltså om alla bitpar ger propagate och carry-in måste rippla 28
29 genom alla 24 bitpar. Detta förhindrar man i en carry-look-ahead adderare genom att titta på propagate signalerna på fyra stycken bitpar i rad. Om alla propagete-signaler är 1 går carry-in för det 4-bitars blocket direkt förbi via en multiplexer till nästa 4-bitars block. Värsta fallet för ripple-fördröjningen kommer nu att minska till 3 stycken ripplingar och 5 stycken multiplexrar (generate i första bitparet och resten propagate). För att i BP-steget ska kunna förutsäga resultatets bergerkod måste den veta antalet nollor som carry-kedjan innehåller. Därför genereras en bergerkod från carry-kedjan via M1 och en bergerkodsgenerator. AND/OR/XOR Dessa instruktioner utförs bitvis på operanderna. För att kunna förutsäga resultatets bergerkod i BP-steget måste man vid AND även ta fram bergerkoden till resultatet för OR och vid OR och XOR bergerkoden för resultatet av AND mellan operanderna. De båda bergerkoderna genereras genom multiplexrarna M0 och M1. Skiftare Skiftaren är uppbyggd som en barrelskiftare men tar även vara på bitarna som skiftas ut för att kunna kontrollera skiftningen i BP-steget (Genom multiplexrarna M0 och M1). Skiftenheten klarar 4 st olika skiftningar, se tabell 5. Skifttyp Funktion (1 steg) Beskrivning LLS (logic left shift) (x n, x n-1,, x 2, x 1 ) (x n-1, x n-2,, x 1, 0) Skiftar Y antal steg åt vänster. Skiftar in nollor LRS (logic right shift) (x n, x n-1,, x 2, x 1 ) (0, x n,, x 3, x 2 ) Skiftar Y antal steg åt höger. Skiftar in nollor ALS (arithmetic left shift) (x n, x n-1,, x 2, x 1 ) (x n-1, x n-2,, x 1, 0) Skiftar Y antal steg åt vänster. Skiftar in nollor ARS (arithmetic right shift) (x n, x n-1,, x 2, x 1 ) (x n, x n, x n-1,, x 3, x 2 ) Skiftar Y antal steg åt höger. Skiftar in signbiten. Tabell 5: Funktion hos olika skifttyper Se bilaga 8. Vid aritmetisk skiftning åt höger är sign satt hög så att bit 23, teckenbiten, skiftas in. B0-B4 från Y styr multiplexrarna M0-M4 och M5-M9. Om en bit är satt skiftas X via multiplexrarna M0-M4 1, 2, 4, 8, respektive 16 steg. Vid inskiftning av ettor läggs det som skiftas ut in i OUT_SHIFT-bussen via multiplexrarna M5-M9. Vid inskiftning av nollor läggs istället inversen till det som skiftas ut in i OUT_SHIFT-bussen. Detta gör att OUT_SHIFT-bussen vid inskiftning av ettor kommer att innehålla lika många nollor som skiftats ut och vid inskiftning av nollor kommer den att innehålla lika många nollor som tillkommit. Komparatorn C0 jämför om Y motsvarar en skiftning mer än 23 steg. Om så är fallet kommer all data skiftas ut och ersättas med signbitar och datat hamnar i OUT_SHIFTbussen. Detta sker via multiplexrarna M10 och M11. Skiftning åt vänster är uppbyggd på samma sätt som skiftning åt höger. Logisk skiftning innebär att sign alltid är låg och att det alltid skiftas in nollor. Compare(CMP) Instruktionen CMP jämför om B är större än A. För att göra det utförs subtraktionen A-B i Carry-look-ahead adderaren. Multiplexern M2 väljer utifrån teckenbiten på resultatet mellan 1 och 0 med tillhörande bergerkoder. Är B större än A blir subtraktionen negativ och teckenbiten satt. Resultatet Q ut från EX-steget blir då via M3 1 med tillhörande bergerkod. Märk att bergerkoden QC som går vidare till BP-steget tillhör resultatet från subtraktionen och inte resultatet från CMP. Detta för att kunna kontrollera att subtraktionen utförts rätt. 29
30 Övriga instruktioner För alla andra instruktioner sker något av ovanstående i EX-steget, vanligtvis addition. Se bilaga 1 för exakt information om vad instruktionerna utnyttjar för funktion i EX-steget. Bergerkodsgenerator Bergerkodsgeneratorn tar ett 24-bitars tal och räknar antalet nollor i det som sedan blir bergerkoden till talet. Eftersom bergerkoden måste beräknas under en klockcykel kan inte en enkel räknare användas för att generera bergerkoden. Att rada upp 24 stycken räknare i rad är inte heller en bra lösning på det skulle innebära en lång tidsfördröjning att rippla igenom och mycket hårdvara. Problemet löstes istället på följande sätt. Talet delas först upp i åtta stycken 3-bitars tal som går in i en 0 s counter som genom ett logiskt grindnät ger ut ett 2-bitars tal med antalet nollor från 3-bitars talet. Dom åtta 2- bitars talen adderas sedan genom sju adderare till en 5-bitars bergerkod som då kommer att innehålla antalet nollor i det ursprungliga 24-bitars talet. ALU_DATA och ALU_ADDR är resultatet och återskrivningsadressen till registret. ALU_DATA och ALU_ADDR går ut ur EX-steget utan register och tillbaka till forwardingen i ID-steget. Detta för att förhindra en delay-slot mellan två instruktioner som använder samma register. XC och YC är bergerkoderna till operanderna X och Y och används senare i BP-steget för att förutsäga resultatets bergerkod. För att förutsäga bergerkoden till resultatet från EX-steget räcker det inte med operandernas bergerkoder. Man behöver även en bergerkod CC som är bergerkoden som genereras av resultatet ut från M7 och är olika beroende på vilken instruktion det är. Se ovan. QC är den genererade bergerkoden till resultatet och jämförs i BP-steget med den beräknade bergerkoden för att validera att resultatet är rätt. Vipporna D0-D14 utgör stegets register och vidarebefordrar signaler till BC-steget. FAILURE BUS Följande bitar sätts i failure_bus av EX-steget: B5 B_OK xor B5(ID) B6 EX_failure and B6(ID) Illegal instruction Detta block är konstruerat med följande VHDL-beskrivningar (bilaga 13; KRETS 1), EX Port map fil för EX-steget samt pipelineregister ALU Genomför aritmetiska-, logiska och skiftoperationer BC-steget FUNKTION Blockets syfte är att fördröja instruktionsflödet genom pipelinen med en klockcykel så att felsignalerna från bergergeneratorn (i EX-steget) och från bergerprediktorn (i BP-blocket) ska synkroniseras till den aktuella instruktionen. FELDETEKTERING BP (Berger-Predict) blocket förutsäger en bergerkod med hjälp av information om bl.a. specifik operation, samt det behandlade datats bergerkoder från 0EX-steget. Den förutsagda bergerkoden jämförs sedan med den tidigare av EX-steget genererade bergerkoden från operationens resultat. Om bergerkoderna inte överensstämmer sätts felsignalen berger_failure2 hög. 30
31 TEKNISK BESKRIVNING Se bilaga 5 Steget tar emot den från BP-blocket (se KRETS 2) genererade bergerkoden och jämför den i komparatorn C0 med bergerkoden från resultatet av operationen i EX-steget. Om dessa inte är lika sätts signalen B1F. BC-steget tar även emot signalen B2F från BPblocket. Syftet med BC-steget är att sätta B2F i samma cykel som B1F. Vipporna D0-D8 utgör stegets register och vidarebefordrar signaler till WB-steget. FAILURE BUS Följande bitar sätts i failure_bus av BC-steget: B7 B2F and B7(EX) B8 B1F and B8(EX) Detta block är konstruerat med följande VHDL-beskrivning (bilaga 13; KRETS 1), BC Komparator samt pipelineregister WB-steget FUNKTION Detta steg bestämmer vad resultatet från EX-steget ska användas till. Det finns 5 alternativ: Tillbakaskrivning av beräknat resultat till registerbanken, tillbakaskrivning från IO-portarna till registerbanken, tillbakaskrivning från data minnet till registerbanken, skrivning till IO-portar och skrivning till dataminnet FELDETEKTERING I WB steget jämförs om den inkommande operationskoden (OP) är den från föregående instruktion lagrade instruktionen (NOP) som komplement till IF steget i vilket samma jämförelse görs. Om jämförelsen visar olikhet sätts felsignalen WB_failure hög. Multiplexern som väljer vad som ska skrivas tillbaka till registerbanken skyddas av TAGs som är förutsagda av assemblatorn. TEKNISK BESKRIVNING Se bilaga 6 Skrivning till dataminnet (SW) De ovan beskrivna felupptäckande funktionerna illustreras av följande: C0 Kontrollerar om destinationsadressen (A_DESTin) avser register nr. 31 C1 Genomför NOP-test C2 kontrollerar om instruktionen är en TRAP Vid skrivning till dataminnet kommer adressen på bussen RESin och datat på bussen D_DESTin. OEinv sätts hög för att möjliggöra skrivning till minnet. Write-pulsen till minnet fås genom att grinda WEinv från OP-decode med CLK-signalen. WEinv och OEinv är grindad med signalen disable så att inget skrivs till dataminnet vid händelse av fel. Läsning från dataminnet (LDW) Vid läsning från dataminnet hålls OEinv låg och WEinv sätts hög för att göra läsning från minnet möjlig. Multiplexern M1 ställs så att D_DESTout får datat från bussen från minnet, vilket gör att data kommer att skrivas tillbaka på adress A_DESTout i registerbanken. 31
32 Skrivning till IO-portarna (PUT) Vid skrivning till IO-portarna sätts signalen IO_RW till IO-portarna hög. Datat som ska skrivas ligger på DATA_IOout och kommer från RESin. Masken som bestämmer vilka bitar som ska ändras ligger på IODDR och kommer från D_DESTin. IO_RW är grindad med disable så att inget skrivs til IO-portarna om ett fel detekterats. För utförligare beskrivning om IO-portarna se avsnitt Läsning från IO-portarna (RIO) Vid läsning från IO-portanra sätts multiplexern M1 så att DATA_IOin skrivs tillbaka på adressen A_DEST i registerbanken. För utförligare beskrivning om IO-portarna se avsnitt Definiering av IO-portarna (PRT) Innan IO-portarna kan användas måste dom konfigureras med kommandot PRT så att vilka bitar som ska vara ingångar respektive utgångar är definierat. Ingångarna kan även förses med en prioritet så att varje bitpar från IO-portarna antingen ska vara inverterade eller lika beroende på vilken prioritet ingången har. IODDR som sätter in- respektive utgångar kommer från RESin och IOPRI som sätter prioriteten kommer från D_DESTin. Signalen PRI aktiverar funktionen och är grindad med disable så att inget sker vid händelse av fel. Övriga instruktioner Vid alla andra instruktioner förutom ovan nämnda sätts multiplexern M0 så antingen D_DESTin eller RESin skrivs tillbaka på adressen A_DESTin i registret. Se bilaga 1 för mer information om vilka instruktioner som skriver tillbaka vad. Feldetektering Signalen WB_failure sätts om NEXTOP från föregående instruktion och OP från nuvarande instruktion inte stämmer överens, undantag sker vid händelse av trap. Signalen sätts även om återskrivningsadressen A_DEST är den skyddade adressen 31 om det inte är TRAP. Testet sker i komparatorerna C0-C3 och det efterföljande logiska grindnätet. Ingångarna på multiplexern M0 är försedda med varsin identitet (TAG). En komparator efter M0 kontrollerar identiteten och sätter signalen mux_failure om inte rätt identitet (TAG) påträffas. Signalen disable sätts om någon bit i FAILUREBUS är satt (detta kontrolleras av C3). Signalen spärrar all skrivning till IO-portarna, dataminnet och registerbanken. Vippan som håller disable nollas från felhanteraren med signalen reg_disable när den går från hög till låg. Detta block är konstruerat med följande VHDL-beskrivning (bilaga 13; KRETS 1), WB Pipelineregister, multiplexer för återskrivning och kontrollogik för skrivning/läsning till IO-portar och dataminne IO-portar FUNKTION IO-portarna är utformade så att det går att definiera vilka IO-pinnar som är utgångar respektive ingångar. Detta görs med en speciell instruktion (PRT) som skriver till IOportens datariktningsregister (DDR). Processorn har två separata IO-portar med 12 IOpinnar vardera. Om feltyst läge inträdes kommer samtliga utgångar hos båda IO-portarna att nollas. En av IO-portarna är ansluten genom den andra kretsen som har förmågan att nolla samtliga utgångar. 32
33 SKRIVNING Vid skrivning till IO-portar matar processorn ut samma data till båda IO-portarna. Om en IO-port har fallerat måste applikationen i vilken processorn är placerad upptäcka detta. För att specificera vilken/vilka IO-pinnar som ska förändra sitt värde ges en bitmask till IO-porten. LÄSNING Båda IO-portarnas ingångar läses samtidigt och sammanfogas beroende på prioritet och skrivs tillbaka till registerbanken med tillhörande statusbitar och en genererad bergerrkod. Samtliga IO-protar är skrivna i VHDL-koden för att fungera i det labsystem som lånades av Chalmers tekniska högskola. Detta innebär att den specificerade funktionen är bortkommenterad i koden. Orsaken till detta är att det FPGA:n på labkortet kommunicerade med IO-pinnar via en CPLD. Det fanns endast fanns en FPGA och det är inte möjligt att specificera en kommunikation med tristatebuffrar i en och samma krets (IOportB och IOportC). TEKNISK BESKRIVNING Ges i avsnitten samt IO-port A Se figur 6 I registret REG_DDR lagras vid PRT vilka bitar som är ut- respektive insignaler. Utgångarna på registret är kopplat till tristatebuffrarna så att de bitar i REG_DDR som är satt till noll sätter buffern i tristate och således blir ingångar. Vid PUT kommer data som ska skrivas till utgångarna på IOout och masken på DDR. Multiplexern M0 styrs bitvis av DDR och väljer mellan IOout och det gamla portdatat så att bara de bitar i DDR som är satt till noll ändras. Registret PORT_DATA håller sedan värdet på utgångarna fram till nästa PUT-instruktion. En READ-instruktion väljer via M1 mellan IOport-utgången och PORT_DATA beroende på REG_DDR så att de bitar som är konfigurerade som ingångar läses från porten och dom som är utgångar läses från PORT_DATA. Resultatet hamnar på IOin. Vid reset nollställs REG_DDR så att alla bitar på IOporten ses som ingångar. Det gör att om porten är försedd med pulldown så kommer de bitar som övriga systemet tror är utgångar tolkas som nollor. Vid SAFE_STATE nollställs PORT_DATA och de bitar som är definierade som utgångar tvingas till noll. REG DDR (data direction register) DDR D Q USE_IO RESET OP S R CO M0 1 IOout 0 D Q IOport RW SAFE_STATE SAFE_STATE2 SAFE_STATE3 IOin or S R PORT DATA 1 0 M1 figur 6: IO-port A 33
34 Om processorn försätts i feltyst läge indikeras detta med 3 signaler till IO-port A: SAFE_STATE Kommer från felhanteraren i KRETS 1 SAFE_STATE2 Kommer från felhanteraren i KRETS 2 SAFE_STATE3 Kommer från pulsräknaren i KRETS 1 Detta block är konstruerat med följande VHDL-beskrivning (bilaga 13; KRETS 1), io_port Enligt ovanstående beskrivning IO-port B Se figur 7 IO-port B fungerar på samma sätt som IO-port A förutom att vid PRT sätts IOportutgången till DDR via M2 och CONF_DDR sätts hög så att REG_DDR i IO-port C kan konfigureras. DDR USE_IO RESET REG DDR (data direction register) D Q S R CONF_DDR or IOout 1 0 M0 D Q 1 0 M1 IOport RW SAFE_STATE SAFE_STATE2 SAFE_STATE3 IOin or S R PORT DATA M2 1 0 figur 7: IO-port B Om processorn försätts i feltyst läge indikeras detta med 3 signaler till IO-port B: SAFE_STATE Kommer från felhanteraren i KRETS 1 SAFE_STATE2 Kommer från felhanteraren i KRETS 2 SAFE_STATE3 Kommer från pulsräknaren i KRETS 1 Detta block är konstruerat med följande VHDL-beskrivning (bilaga 13; KRETS 1), ioportb Enligt ovanstående beskrivning IO-komparator PRI=0 A B Q OK PRI=1 A B Q OK Tabell 6: Sanningstabeller över sammanfogningen av insignalerna. Detta block sammanfogar insignalerna från IO-portarna och adderar en bergerkod till det resulterande datat. Sammanfogningen av två insignaler kan göras på två sätt enligt sanningstabellerna ovan beroende på vilken prioritet insignalsbiten har. PRI=0 innebär att insignalen från IO-port B ska vara inverterad den från IO-port A. OK-signalen sätts till noll på de ogiltiga värdena när insignalsbitarna är lika. PRI=1 innebär att insignalerna från IO-portarna ska vara lika och OK-signalen sätts då till noll när bitarna inte har samma värden. Databitarna Q läggs på bitarna (0:11) och OK-bitarna läggs på bitarna 34
35 (12:23) på den resulterande databusssen IO. Vilken av sanningstabellerna som används till respektive insignal bestäms av registret PRI REG som programmeras av signalen set_pri med data PRIORITY. PRIORITY SET_PRI RESET IO_A IO_B PRI REG (priority register) D Q S R M0 and 1 Q and 0 b11:0 b23:21 b20:18 b5:3 Bergerkodsgenerator 0 s counter 0 s counter 0 s counter 2-bits 2-bits 2-bits 4-bits adder 4-bits 4-bits adder 4-bits 3-bits 2-bits adder 5-bits bergerkod xnor xor M1 1 0 OK b23:12 b23:0 b2:0 0 s counter 2-bits b28:24 figur 8: IO-komparator b23:0 b28:0 IO FELHANTERAREN FUNKTION Samtliga av ovan nämnda felsignaler är anslutna till en buss failure_bus som genomlöper alla register. Denna buss är efter WB steget ansluten till en felhanterare. Om felhanteraren upptäcker att fel (dvs. >0 bitar i bussen är ettor) har detekterats kommer felhanteraren att exekvera om instruktionen. Om samma fel kvarstår när instruktionen når felhanteraren nästa gång försätts processorn i feltyst läge. Om det första felet inte kvarstår men ett nytt har tillkommit kommer felhanteraren att exekvera om instruktionen en gång till. Felhanteraren upphör att exekvera om instruktionen först när samtliga bitar i failure_bus är låga. FELDETEKTERING Det finns ingen feldetektering i felhanteraren, istället är den dubblerad så att den andra felhanteraren är placerad i en separat komponent. TEKNISK BESKRIVNING Se bilaga 7 Felhanteraren tar emot FAILUREBUS och bestämmer om säkert läge ska inträda, om en instruktion ska köras en gång till eller exekveringen ska fortlöpa. Felhanteraren består av en tillståndsmaskin med följande 4 tillstånd: RESET, IDLE, WAIT och SAFE. Vid reset nollställs alla utsignaler varefter tillståndsmaskinen övergår (A) i tillståndet IDLE. I IDLE kontrolleras FAILUREBUS bitvis och om någon bit i bussen är hög sätts reset_bus (se nedan), biten lagras i det temporära registret tmp_failure, signalerna retry och reg_disable sätts höga och tillståndet byts (C) till WAIT. reset_bus är en 5 bitar bred buss, varje bit i bussen nollställer ett register i pipelinen. reg_disbale förhindrar skrivning till registerbanken, dataminnet och IO-portarna. retry ges till IF-steget som då läser upp den instruktion som medförde en hög bit i failure_bus. Eftersom reset_bus har satts, kommer endast NOP-instruktioner att ligga i pipelinen. Samt den instruktion som återlästs i IF-steget. Tillståndsmaskinen befinner sig i WAIT i 4 cykler (tills den återlästa instruktionen igen når WB-steget). Därefter byts tillståndet tillbaka (D) till IDLE. Om samma fel medföljt den återlästa instruktionen upptäcks detta 35
36 med hjälp av tmp_failure. Då övergår (B) tillståndsmaskinen till SAFE. Om den återlästa instruktionen inte har något medföljande fel nollställs tmp_failure och reg_disable. Om instruktionen saknar det tidigare felet men har ett nytt körs den om igen på samma sätt som ovan. En räknare kontrollerar om den återkörda instruktionen nått WB-steget. Räknaren startar då flaggan count går hög (då WAIT inträdes) och sätter flaggan counted då den återlästa instruktionen genomlöpt pipelinen. I tillståndet SAFE sätts reset_bus enligt nedan, retry nollställs och safe samt reg_disble sätts höga. Enda möjligheten att återgå från SAFE till IDLE är via RESET. För alla upptäckta fel i IDLE sätts reset_bus = b (b5 motsvarar IF-steget). I WAIT sätts reset_bus = b I SAFE sätts reset_bus = b Failurebus innehåller följande signaler: bit 0 IM_FAILURE Felsignalen indikerar att PCS-testet upptäckt ett fel bit 1 bit 2 bit 3 bit 4 bit 5 bit 6 bit 7 bit 8 bit 9 INSTR_FAILURE Felsignalen indikerar att NOP- eller bergerkodstestet för hela instruktionen har upptäckt ett fel ADDR_FAILURE Felsignalen indikerar att felaktig mål-/destinationsadress angivits vid TRP/RFT BRANCH_FAILURE Felsignalen indikerar att en okänd kombination av insignaler givits BRANCHblocket DECODE_FAILURE Felsignalen indikerar att en okänd kombination av insignaler givits DECODEblocket (operationskod) BRANCH_TAKEN xor B_OK Felsignalen indikerar att ett hopp är taget men att fel upptäckts vid test av hoppvillkoret eller tvärt om ALU_FAILURE Felsignalen indikerar att en okänd kombination av insignaler givits ALU:n (operationskod) BERGER2_FAILURE (B2F) Felsiganlen indikerar att avvikelse upptäcks vid jämförelse av genererad och predikterad bergerkod i BP-blocket BERGER1_FAILURE (B1F) Felsiganlen indikerar att avvikelse upptäcks vid jämförelse av genererad och predikterad bergerkod i BC-blocket WB_FAILURE Felsignalen indikerar att fel upptäckts vid NOP-test bit 10 IMM_XIMM_FAILURE Felsignalen indikerar att fel upptäckt i TAG-test vid avkodning av SRC2 36
37 bit 11 FORW_FAILURE Felsignalen indikerar att fel upptäckt i TAG-test för forwarding-blocket bit 12 RBANK_FAILURE or MUX_FAILURE2 Felsignalen indikerar upptäckt adresseringsfel vid läst data från registerbanken och/eller i TAG-test för återskrivning av data i WB-steget bit 13 MUX_FAILURE1 Felsignalen indikerar upptäckt fel vit TAG-test för återskrivning av data i WBsteget Detta block är konstruerat med följande VHDL-beskrivning (bilaga 13; KRETS 1), FAULT Enligt ovanstående beskrivning 8.2 KRETS BP-blocket FUNKTION Detta block predikterar bergerkoden för en aritmetisk operation. Syftet med att prediktera bergerkoder är att det ej är nödvändigt med dubblering av ALU:n. En ytterligare fördel med bergerkoder är att dom även fungerar som en checksumma. TEKNISK BESKRIVNING Addition För att addera 2 st n-bitars tal kan vi representera dom som X=(x n,, x 2, x 1 ) Y=(y n,, y 2, y 1 ) och få summan Q=(q n,..., q 2, q 1 ) med dom interna carry-bitarna C=(c n,, c 2, c 1 ) Där x i, y i, q i, c i {0,1}, operationen för i:te biten kan skrivas som x i + y i + c i-1 = 2c i + q i = (c i + q i ) + c i (1) Låt N(X) vara antalet ettor i den binära representationen av X, N(x i )=x i. N(X) + N(Y) + c in = N(C) + N(Q) + c out (2) Där c in = c i-1 och c out = c n För att representera (2) i bergerkoder inför vi XC = n-n(x) där XC är antalet nollor i X, dvs. bergerkoden för X. Ekvation (2) kan då skrivas om som. QC = XC + YC CC c in + c out (3) 37
38 Subtraktion Vid 2-komplement subtraktion inverteras Y och c in sätts hög. På samma sätt som ovan kan följande bevisas. N(X) + N(Y ) + c in = N(C) + N(Q) + c out (4) N(Y ) = YC eftersom antalet ettor i Y invers måste vara samma som antalet nollor i Y. XC = n N(X) insatt i (4) ger. n XC YC + c in = N(C) + n QC + c out (5) QC = XC YC + N(C) c in + c out (6) Eftersom N(C) inte är bergerkoden till carrykedjan utan antalet ettor så räknas antalet ettor i carrykedjan i EX-steget och inte antalet nollor som vid addition. AND/OR/XOR AND x i y i q i 1 s lost OR x i y i q i 1 s lost XOR x i y i q i 1 s lost Från sanningstabellerna ovan kan man härleda ekvationer för bergerkodsprediktionen. För exempelvis Q = X XOR Y blir antalet ettor som följer. N(X) + N(Y) = N(Q) + 2N(X AND Y) (7) Insättning av XC = n N(X) ger n XC + n YC = n QC + 2(n (X AND Y)C) (8) QC = XC + YC 2(X AND Y)C + n (9) På liknande sätt blir Q = X AND Y QC = XC + YC (X OR Y)C (10) Q = X OR Y QC = XC + YC (X AND Y)C (11) CC från EX-steget kommer vid OR och XOR innehålla (X OR Y)C och vid AND innehålla (X AND Y)C. Se även [BERGERCODE]. Skifter Eftersom CC vid logisk skiftning och aritmetiskskiftning när signbiten inte är satt kommer att innehålla antalet nollor som tillkommit vid skiftningen beräknas bergerkoden enligt följande ekvation. QC = XC + CC (12) 38
39 Vid aritmetisk skiftning när signbiten är satt kommer CC innehålla antalet nollor som skiftats ut. Ekvationen för bergerkodsberäkningen blir således. QC = XC CC (13) Övriga instruktioner Övriga instruktioner utnyttjar någon av ovanstående instruktioner, i de flesta fall addition. Ekvationerna ovan realiseras i hårdvara enligt bilaga 9. BP-blocket ger även ut en felsignal B2F om den genererade bergerkoden från EX-steget inte stämmer överens med den beräknade bergerkoden. Jämförelsen sker i komparatorn C0. Detta block är konstruerat med följande VHDL-beskrivning (bilaga 14; KRETS 2), BERGER_prediction Enligt ovanstående beskrivning IO-port C Se figur 9. Vid normal operation är IO-port C helt transparant, men man har vid händelse av fel möjlighet att sätta porten i felsäkert läge oberoende av IO-port B. Vid PRT konfigureras REG_DDR med hjälp av data från IO-port B så att tristate-buffer T1 aktiveras för de bitar som är definierade som utgångar i REG_DDR och tristate-buffer T0 aktiveras för bitarna som är ingångar. Märk att vippan D1 set-signal går låg när REG_DDR konfigureras så att inte IOut ändras under konfigurationen. Vid SAFE_STATE sätts vippan D0 så att vippan D1 nollställs och hålls låg fram till en RESET. Detta göra att alla utgångar på IOut nollställs och hålls låga fram tills processorn får resetsignal. REG DDR (data direction register) D Q CONF_DDR RESET S R or IOin D Q IOout SAFE_STATE SAFE_PULSE or S Q R D0 or S R figur 9: IO-port C D1 Om processorn försätts i feltyst läge indikeras detta med 2 signaler till IO-port C: SAFE_STATE Kommer från felhanteraren i KRETS 2 SAFE_PULSE Kommer från pulsdetektorn i KRETS 2 Detta block är konstruerat med följande VHDL-beskrivning (bilaga 14; KRETS 2), IOportc Enligt ovanstående beskrivning Pulsdetektorn Genom varje piperegister går en signal pulse som byter tillstånd då pipeklockan ändrar tillstånd. Denna signal är efter pipelinen ansluten till KRETS 2 i vilken en pulsdetektor finns. Pulsdetektorn är en räknare samt tillståndsmaskin med 3 tillstånd (s1, s2 och s3). 39
40 Räknaren räknar med KRETS 2 s klocka. Om signalen pulse går hög ändras tillståndet hos tillståndsmaskinen till exempelvis s2. Om tillståndsmaskinen når s3 nollställs räknaren och tillståndet återställs till s1. Om tillståndsmaskinen inte når s3 och räknaren räknar till 8 sätts processorn i feltyst läge. Pulsdetektorn är dubblerad och finns även i KRETS 1. Detta block är konstruerat med följande VHDL-beskrivning (bilaga 14; KRETS 2), PULSE_COUNTER Enligt ovanstående beskrivning 9 Feleffektsanalys Nedanstående feleffektsanalys är genomförd på en funktionell systemnivå och syftar till att visa hur dataflödet genom processorn kontrolleras med avseende på enkelfel. Analysen visar också vilka signaler i failurebus som sätts i olika delar i processorn. Nr. Block Funktion Felfall Åtgärd Failure bus 1. IF Läsning av instruktion från Bitfel i läst data Upptäcks i INB-testet Instr_failure IM 2. IF Läsning av instruktion från Bitfel i PC (felaktig Upptäcks i PCS-test Im_failure IM Instruktion) och/eller i NOP-test 3. IF Addition till PC Låser sig eller räknar fel Upptäcks i PCS-test Im_failure och/eller i NOP-test] 4. IF Addition till PC MEM_COUNTER låser sig Upptäcks i PCS-test Im_failure eller räknar fel och/eller i NOP-test 5. IF RETRY Någon av stackarna PCS-, Upptäcks i PCS-test Im_failure NOP- eller PC-stack innehåller bitfel eller felaktig data och/eller i NOP-test 6. IF RETRY PIPE_COUNTER räknar fel Upptäcks i PCS-test Im_failure eller är låst till ett värde och/eller i NOP-test 7. IF TRAP Registren ger fel data då Upptäcks i NOP-test Im_failure ins_nop ska fogas in 8. IF TRAP Registren ger fel data då trap Upptäcks i NOP-test Im_failure ska fogas in 9. IF TRAP Signalerna HW_TRAP, BUSY, TRAP, ins_nop kommer inte i förväntad följd Upptäcks i NOP-test Im_failure 10. IF TRAP Signalen HW_TRAP låst till 0 eller IF TRAP Komaratorn som upptäcker TRAP (instruktionen), som då skriver till NOP_trap och PCS_trap, ger fel signal 12. IF TRAP Komparatorn signalerar inte om BEQ/BNE exekveras just då ett hårdvarugenererat avbrott ges 12. IF RFT Komaratorn som upptäcker instruktionen RFT ger fel signal 13. IF RFT Fel data skrivet i PCS_trap eller NOP_trap. 0 Hårdvarustyrt avbrott bortkopplat 1 Ett hårdvarustyrt avbrott kan genomföras Upptäcks vid RFT i NOP- och/eller PCS-test Upptäcks eftersom TRAP infogar två instr. Vilka ej = Next OP efter hoppet Upptäcks i PCS-test och/eller i NOP-test Upptäcks i NOP-test eller i PCS-test 14. ID Instruktionsavkodning Fel OP-kod ges till DECODE Upptäcks av komparatorn 15. ID Instruktionsavkodning DECODE sätter inte Upptäcks inte (1) trap_busy då instruktionen TRAP fås 16. ID Instruktionsavkodning DECODE nollställer inte trap_busy då instruktionen RFT fås Inget mer avbrott tillåts 17. ID Instruktionsavkodning Felaktiga styrsignaler ges Beror på vilken styrsignal felet påverkar 18. ID IMM/XIMM Felaktig adresseringsmod Upptäcks av bergerkodstest med IMB 19. ID IMM/XIMM Felaktig teckenförlängning Upptäcks av Bergerkodstest med Upptäcks inte (1) Im_failure Im_failure Im_failure Im_failure decode_failure Upptäcks inte (1) Upptäcks inte (1) Failurebus (4) B1F B1F 40
41 IMB 20. ID IMM/XIMM Felaktig adress vid Upptäcks i adresstest Addr_failure TRAP/RFT 21. ID Branchning Hoppet tas aldrig Felet upptäcks av B1F Bergerkodstest i BCsteget 22. ID Branchning Hoppet tas alltid Felet upptäcks av B1F Bergerkodstest i BCsteget 23. ID Branchning Hoppadress felaktigt beräknad Felet upptäcks av PCStest Instr_failure i IF-steget 24. ID Registerbank Skriver till fel adress Upptäcks vid läsning av Rbank_failure datat. Läst adress jämförs med adress i datat 25. ID Registerbank Skriver felaktigt data Upptäcks av B1F och B2F Bergerkodstest i EX och BP då datat används 26. ID Registerbank Läser från fel adress Samma som för Rbank_failure skrivning till fel adress 27. ID Registerbank Reg_disble låst till 1 eller 0 Signalen är dubblerad Ej tillämplig 28. ID Forwarding Tar emot fel adress Upptäcks av TAG test Forw_failure 29. ID Forwarding Tar emot fel data Upptäcks av B1F och B2F Bergerkodstest i EX och BP då datat används 30. ID Forwarding Fel i komparator Upptäcks av den andra Forw_failure komparatorn 31. ID Forwarding Fel i multiplexer Upptäcks av Forw_failure 32. EX ALU Beräkningsfel Upptäcks av B1F och B2F Bergerkodstest 33. EX ALU Operationsfel Upptäcks av avkodaren Alu_failure 34. EX Skiftenhet Fel i operation Upptäcks av B1F och B2F Bergerkodstest 35. EX Skiftenhet Teckenbitsfel Upptäcks av B1F och B2F Bergerkodstest 36. EX Val mellan ALU, skiftenhet Fel i multiplexer Upptäcks av B1F och B2F och logisk operation (motsvarande M1) Bergerkodstest 37. EX Val mellan ALU, skiftenhet Fel i multiplexer Upptäcks av B1F och B2F och logisk operation (motsvarande M2) Bergerkodstest 38. EX Bergerkodsgenerator Fel i bergerkodsgenerator Upptäcks av B1F och B2F Bergerkodstest 39. EX Kontroll vid hopp Fel i komparator eller i Upptäcks av B1F och B2F kombinatorisk logik Bergerkodstest 40. EX Logik för ADDV och Fel i logik för ADDV och Upptäcks av Ej tillämplig SUBV SUBV programvara 41. BC Bergerkodskomparator Ger felaktigt resultat Komparatorn i BPblocket B2F fungerar fortfarande 42. WB Kontroll av NOP och TRAP Fel i komparatorer Upptäcks av Ej tillämplig programvara 43. WB Kontroll av NOP och TRAP Fel i kombinatorisk logik Upptäcks av Ej tillämplig programvara 44. WB Avkodning av OP-kod Ger felaktigt resultat Upptäcks av TAG-test Mux_failure 45. WB Styrning av OEinv och Weinv Ger felaktig(a) signal(er) Upptäcks av mjukvara Ej tillämplig 46. WB Läsning skrivning av DM Fel i cykelräknare COUNTER 47. WB Läsning skrivning av DM Fel i komparatorer eller vippor Upptäcks då datat används i en aritmetisk operation med Bergerkodstest Upptäcks då datat används i en aritmetisk operation med Bergerkodstest 48. WB Läsning skrivning av DM Fel i läst/skrivet data Upptäcks då datat används i en aritmetisk operation med Bergerkodstest 49. WB Läsning skrivning av DM Fel i läs/skriv adress Upptäcks av programvarutest 50. WB Styrning av DISABLE Fel i kombinatorisk logik eller i vippa 51. WB Val av data som ska skrivas tillbaka D_DESTout Fel i motsvarande multiplexer Mx Skrivning till registerbanken förhindras av oberoende signal (extra_check) Upptäcks i TAG test B1F och B2F B1F och B2F B1F och B2F Ej tillämplig Ej tillämplig Mux_failure 41
42 52. BP Bergerkodsprediktering Bergerkoden felpredikterad Upptäcks vid jämförelse med den framräknade Bergerkoden 53. BP Jämförelse av bergerkoder Fel i komparator Upptäcks av komparatorn i BC-steget 54. IOa Datariktningsregister (DDR) Fel i styrning DDR Upptäcks av applikationen eller av mjukvaran (IOa och IOc ej lika) 55. IOa Datariktningsregister (DDR) Fel i DDR:S innehåll Upptäcks av applikationen eller av mjukvaran (IOa och IOc ej lika) 56. IOa Skrivning av data (PORT DATA) 57. IOa Skrivning av data (PORT DATA) Fel i multiplexern M0 Fel i registret PORT DATA Utgångarna skiljer sig från IOb och IOc, upptäcks av applikationen Utgångarna skiljer sig från IOb och IOc, upptäcks av applikationen 58. IOa Läsning av data Fel i multiplexern M1 Upptäcks av mjukvara vid jämförelse med IOb 59. IOa Läsning av data Fel i läst data Upptäcks av mjukvara vid jämförelse med IOb 60. IOa Försätta IO-porten i Funktion upphörd IOb och IOc kan säkerthetstillstånd fortfarande nå säkert läge 61. IOb Styrning av CONF_DDR Fel i logik (andra felfall: se Upptäcks av IOa) processorns applikation 62. IOc Konfigurering av DDR Fel i registrets innehåll Upptäcks av applikation och/eller mjukvara 63. IOc Läsning Data fel Upptäcks av mjukvara vid jämförelse med IOa 64. IOc Skrivning Data fel Upptäcks av processorns applikation 65. IOc Försätta IO-porten i säkerthetstillstånd Fel i hållkrets (D0) IOa kan fortfarande nå säkert läge, felet omhändertas av applikationen IOa kan fortfarande nå säkert läge 66. IOc Försätta IO-porten i säkerthetstillstånd Fel i skrivregister (D1) 67. CMP Sammanfogning av data Funktionsfel hos grind Upptäcks av mjukvarutest om IOa och IOb ej lika 68. CMP Sammanfogning av data Fel i multiplexer Upptäcks av mjukvarutest om IOa och IOb ej lika 69. CMP Sammanfogning av data Fel i prioritetsregistret (PRI) Upptäcks av mjukvarutest om IOa och IOb ej lika 70. CMP Bergerkodsgenerering Fel i funktion Upptäcks av Bergerkodstest i EX och BP-blocket 71. PC PC:ns förmåga att Indikerar alltid korrekt Fel upptäcks av den kontrollera signalen pulse funktion andra pulsräknaren (3) 72. FH Felhanterarens förmåga att En av felhanterarna signalerar FH kontrollerar ej upptäcka fel alltid korrekt funktion varandra (2) 73. PULS Sätta processorn i safe-state Fel i funktion Funktionen vidbehållen av den andra pulsräknaren 74. REG Mellanlagring av data Bit låst Upptäcks av: Berger-, PCS-, NOP-, eller Adress-test 75. FBUS Ge felmeddelande Felsignal konstant värde Upptäcks då instruktionen TST används 76. RBUS Nollställa alla register Resetsignal konstant värde Upptäcks av NOP-test i WB 77. CLK Systemklocka Fel i funktion Upptäcks av motsvarande pulsdetektor i krets vars klocka fungerar B1F och B2F B1F Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig Ej tillämplig WB_failure_out Ej tillämplig 42
43 Den övergripande åtgärden vid ett upptäckt fel är att processorn kör om instruktionen en gång till, om felet kvarstår går processorn i feltyst läge. (1) TRAP-rutinen körs en gång varefter samtliga övriga TRAP-anrop ignoreras av processorn. TRAP-rutinen ska inte användas till funktioner som är viktiga för säkerheten. Se även avsnitt 12. (2) Felhanterarna kontrollerar ej varandra i detta prototypsystem. I stället förutsätts sannolikheten för att ett fel skall uppstå på exakt samma position i en kanal när felet tidigare uppstått i en annan kanal vara mycket låg. Motiveringen till detta är att de båda felhanterarna finns i olika kretsar. Se även avsnitt 12. (3) PC (Pulse Counter) kontrollerar inte varandra. En extern elektronisk anordning ska finnas (watch-dog) som kontrollerar sekvensen samt att sekvensen kontrolleras av mjukvara. (4) Detta felfall kan delas in i många specialfall. Det mest relevanta fallet är branchflag: Om felet inträffar och instruktionen ej är en branch upptäcks detta omedelbart av PCS och NOP-tst. Om instruktionen är tex. RFT som av branchmodulen (BRANCH LOGIC) inte tolkas som ett hopp kommer hoppet inte att tas. Detta måste kontrolleras av mjukvaran. 10 Resultat Resultatet av detta examensarbete är en mikroprocessor samt en assemblator som enligt den feleffektsanalys som är genomförd uppfyller kraven om feltolerans. Dock under vissa förutsättningar, den hårdvarumässiga avbrottsfunktionen ska inte användas för säkerhetskritiska signaler och för att kunna erhålla feltolerans på IO portarna ska endast dynamiska signaler användas till säkerhetskritiska periferienheter. Även ska hänsyn anmärkningarna (1) (4) beaktas. Processorn implementerades i en FPGA Virtex XCV300-bg432 i vilken maximala klockfrekvensen uppskattades till 14 MHz. Processorn upptog 59% av kretsen. Processorn kan återhämta sig från alla fel som den kan upptäcka om felen är transienta. Latenstider för fel: Felen upptäcks i det steg i pipelinen där de uppstår och värsta tänkbara fallet är att ett fel upptäcks i första steget (IF) vilket innebär att det tar 4 cykler innan felet når felhanterarna och ytterligare 5 cykler innan felet är åtgärdat. Med ovanstående implementation blir då latenstiden som längst: 0.6 us Ett demonstrationssystem konstruerades också i form av ett tvåhandsmanöverdon för att visa på processorns funktionalitet. 11 Slutsats Processorarkitekturen som är framtagen vid detta examensarbete är främst avsedd för bruk inom industriell automation. Avvägningen mellan hög prestanda och feltolerans var förutsedd då industriella applikationer sällan ställer krav på hög beräkningshastighet men däremot på feltolerans och robusthet i drift. Detta examensarbete visar att det troligen är möjligt att skapa en enkanalig processorarkitektur vilken även uppfyller de högsta kraven om feltolerans som finns i de vanligaste standarderna med avseende på maskinstyrningar (kategori 4; SS-EN 954-1). 43
44 För att visa på prestanda-/utrymmes-/kostnadsmässiga vinster/förluster för en sådan arkitektur jämfört med en icke feltolerant arkitektur måste dessa jämföras. Detta arbete är inte genomfört på grund av tidsbrist. Det som skiljer denna processorarkitektur från de som tidigare studerats (av författarna) är att den utnyttjar tidsredundans utan förlängning av pipelinen, att assemblatorn är hårdare knuten till processorns hårdvara än de instruktionsuppsättningar som tidigare studerats samt framförallt att processorn är uppdelad i två fristående kretsar (chip). Dock uppnåddes inte den grad av funktionsuppdelning mellan kretsarna som från början avsågs. 12 Diskussion och vidare arbete Under examensarbetets gång har synpunkter på antalet hårdvarugenererade avbrott uppkommit. Under en vidareutveckling av processorn bör den hårdvarumässiga avbrottsfunktion som finns tas bort. Detta för att den som finns tillgänglig inte är feltolerant. Istället bör antalet mjukvarumässiga avbrott utökas i antal. Även bör kommunikationen mellan pipelinen och IO portarna modifieras så en läsning/skrivning av IO portarna egentligen utgörs av två skrivningar/läsningar. Genom att skriva/läsa en port åt gången minskas sannolikheten för att ett sk. common cause failure ska generera samma felaktiga signaler på båda utgående IO portarna. På så sätt kan kravet om dynamiska in-/utsignaler tas bort. Läsningen av instruktionsminnet kan också modifieras så att en instruktion kan läsas som data och därmed möjliggöra ett mera avancerat minnestest i kombination med det som processorn redan hårdvarumässigt genomförs. Detta är vanligt i dagens PIC-processorer. Användning av två redundanta felhanterare är resurskrävande. Detta skulle förbättras genom att modifiera instruktionen TST så att den returnerar värdet på failurebus samt en av felhanterarnas resultat till ett register i registerbanken. Åtgärden möjliggör funktionstest av felhanteraren samt kontroll av samtliga felupptäckande mekanismer med mjukvara. Då kan en av de två felhantrarna reduceras bort med förbättrad feldetektering och i mindre hårdvara som resultat. Syftet med processorn är att endast styra IO portarna och vara feltolerant. Att exempelvis ansluta processorn till flera andra processorer i ett sk. distribuerat styrsystem kräver bl a en mängd avbrottssignaler vilka processorn inte har (enl. ovan). Nästa utvecklingssteg i ett arbete att sätta processorn i ett praktiskt användbart system är att designa ett feltolerant HårdvaruRealtidsOperativSystem (HRTOS). Detta system är placerat mellan instruktionsminnet och processorn och fördelar programminnet i mindre delprogram (tasks) som har prioritet sinsemellan. Vilket delprogram som ska exekveras av processorn bestäms av olika avbrottssignaler som ges till systemet. På detta sätt kan ett väldigt kraftfullt feltolerant styrsystem skapas med möjlighet till kommunikation med andra feltoleranta styrsystem. För praktiskt kunna använda sig av processorn bör verktyg utvecklas med assemblatorn ASRC som grund. Ett sådant verktyg abstraherar bort den lite komplicerade programmeringsformen som processorn har. Innan processorn överhuvudtaget kan godtas som feltolerant måste en analys av dess funktionalitet genomföras av en oberoende part. En del av en sådan analys bör vara felinjicering. 44
45 13 Referenser [SP REPORT 1997:12] Safety Validation of Computer-Based Machine Control Systems [IEC 61508] Functional safety of electrical/electronic/programmable electronic safetyrelated systems [SS-EN 954-1] Safety of Machinery Safety-related parts of control systems Part 1: General principles for design (Utgiven 1998) [BERGERCODE] Concurrent Error Detection In Arithmetic and Logical Operations using Berger Codes; Jien-Chung Lo, Suchai Thanawastien och T.R.N Rao [RISC] Computer Architecture a Quantitative Approach; John L Hennesy och David A. Patterson; ISBN
46 Bilaga 1 Instruktioner Nedan följer en kort beskrivning av funktion och syntax hos alla instruktioner som kan exekveras av den feltoleranta processorn. Aritmetiska instruktioner Följand aritmetiska instruktioner finns tillgängliga: ADD (Aritmetisk addition) SUB (Aritmetisk subtraktion) AND (Aritmetisk logisk AND) ORA (Aritmetisk logisk OR) XOR (Aritmetisk logisk XOR) CMP (Jämförelse mellan två tal) ADV (Aritmetisk addition vilken genererar TRAP vid overflow ) SUV (Aritmetisk subtraktion vilken genererar TRAP vid overflow ) LLS (Logisk skiftning vänster) LRS (Logisk skiftning höger) ALS (Aritmetisk skiftning vänster) ARS (Aritmetisk skiftning höger) Syntax: INSTR DEST REG1 REG2 Adresseringsmoder: Register, immediate, extended immediate Implementation: Resultatet från den aritmetiska operationen mellan REG1 och REG2 skrivs till DEST. Hoppinstruktioner BEQ (Branch if Equal) Syntax: BEQ DEST REG1 NUM Adresseringsmoder: Immediate Implementation:Villkorligt hopp som jämför om DEST = REG1. Om villkoret är uppfyllt sätts PC:n till PC + NUM. BNE (Branch if Not Equal) Syntax: BNE DEST REG1 NUM Adresseringsmoder: Immediate Implementation: Villkorligt hopp som jämför om DEST /= REG1. Om villkoret är uppfyllt sätts PC:n till PC + NUM. TRP (Hårdvaru- eller mjukvarugenererat avbrott) Syntax: TRP DEST R0 NUM Adresseringsmoder: Immediate 46
47 Implementation: Avbrottsinstruktionen är ett ovillkorligt hopp, som alltid genomför hoppet samt alltid har samma destinationsadress. Destinationsadressen ges i NUM, processorn kontrollerar att denna är NUM = 01. Om kompilatorn sätter en annan adress försätts processorn i säkert tillstånd. Den nuvarande PC:n lagras på DEST = R31 i registerbanken vilket också kontrolleras av processorn. RFT (Return From Trap) Syntax: RFT R31 R0 0 Adresseringsmoder: Immediate Implementation: Instruktionen är ett ovillkorligt hopp som sätter PC:n till det tal som finns lagrat i R31. Processorn kontrollerar att DEST = R31. Övriga instruktioner LDW (Load Data Word) Syntax: LDW DEST REG1 REG2 (NUM) Adresseringsmoder: Register, Immediate och Extended Implementation: Ett tal återläses till registret DEST från REG1 + REG2 (NUM). SDW (Store Data Word) Syntax: SDW DATA REG1 NUM Adresseringsmoder: Immediate, Extended Implementation: DATA skrivs till dataminnet på adress REG1 + NUM. RIO (Läs data från IO-port) Syntax: RIO DEST MASK NUM Adresseringsmoder: Immediate Implementation: De ingångar som anges i MASK+NUM läses och lagras i registret DEST. PUT (Skriv data till IO-port) Syntax: PUT MASK REG1 DATA Adresseringsmoder: Immediate Implementation: Instruktionen tar talet REG1+DATA och skriver det på de utgångar som anges i MASK, de andra utgångarna behåller sina tidigare värden. PRT (Port definition, sätt prioritet samt riktning för IO-portar) Syntax: PRT DDR REG1 NUM 47
48 Adresseringsmoder: Immediate Implementation: Instruktionen definierar vilka bitar i IO-porten som ska vara inrespektive utgångar med DDR samt sätter ingångarnas prioritetsregister med REG1+NUM. SFE (Enter safe-state) Syntax: SFE R0 R0 R0 Adresseringsmoder: Register Implementation: Instruktionen försätter processorn i feltyst läge. TST (TEST) Syntax: TST R0 R0 NUM Adresseringsmoder: Immediate Implementation: Instruktionen testar processorns felupptäckande mekanismer. Felhanteraren kontrollerar att samtliga bitar i failure bus är höga då instruktionen exekverats. Om någon bit inte är hög försätts processorn i feltyst läge. NUM är ett tal vilket förses med en felaktig bergerkod av assemblatorn. NOP (No OPeration) Syntax: NOP Adresseringsmoder: Inga (assemblerkommando) Implementation: Instruktionen fördröjer exekveringen med en cykel. END (END of file) Syntax: END Adresseringsmoder: Inga (assemblerkommando) Implementation: Instruktionen är den sista som anges i ett assemblerprogram. I processorn infogas en BEQ R0 R
49 Bilaga 2 IF-steget L 6?$?$ $; ;< ;< R M?D<P I; $ I' 3.1 8C B J 3) 3) 23/ 1),)- ;: =! < $><! 3.1 0/ 23) 77,23) 23) 23) KJL / 23) 77,23) 0/ 6;CC<.4 * 56 :!D NB 6C VW U [Z \ 9 ; A C 21) " 6 B L 8C ' A, M B J B L K $! % ' NC ;% "! J 2 " B 6 "! A, B< " B I? '$ 3.@ 6 " ( 9 9 ;% < 9 ;% < I' 3. ;% < I' E ; "B &< CC; ; "B &C <% < QQ O 6!$ '$ &; % % $ &; $ & C &: B &+ L Q Q Q 0/ 0/ 6T 6T 6T 6T 3) 2 2 6T 8T 8T 77,23) T 8T 8T 0/ 2 0/ &+ *),)- 0./ &% * & C &2/ XVWY XV] _^VW ZW DB %B: '% DB %B: '% &3* '; 6 '; 6 ;% < &! C '; '; ` a b cd MC '6 '% $C 8 B & &3/ 6 '6 '% $C # ' C K ' <)1 &! B< " "! B< " "! &3/ C C L 6 < 2. H # = &% F ; < G $ &%; < :$ ; $!: P% C J +/ 3 &+ )1 e f ;% < &; $%; E, 3/ A L C = &% F ; < 3.@ ;%$; # &: &@ E &: C J 49
50 S ) S [! #' # Y# $# R *#' * # *#Y * $# S &! ) #Y% )# Y#, *, ) #'% * + ) #% # )$% Y S Y ) #% # $ &% DDDDD ' &% ' ) # C ) #% ) #% " $ ) Y + Y ) #'% + ) + ' + ( [ + $ & ' + ) $ + Z + => A + Z C ) #% ) #'%! ) ) ) Bilaga 3 ID-steget. / / 9:. 3; / ; 5 9:. 3; / E E F 6 G E ; E ; 5 F 6 G ; 5 - TXU W! " "!B P #% ) #$% ) # $% HIJ K1 L MNO,, -,, - # # B B! " $ )(( )(( #? )))))&)? ' Q )(( )))))? )( )(( )(( )(( )(( )(( )(( ) TXU W TXU W TXU W TVU W TVU WS TXU W TXU WS & " A - <! ) 50
51 Bilaga 4 EX-steget PULSEin DATA1 DATA2 OPin FAILUREBUSin NEXTOPin D_DESTin A_DESTin CLK RST clear_reg clear_reg2 0 b23 b22:0 0 b23 b22:0 Ki xnor b23:0 b23:0 b28:24 b28:24 OR Carry-look-ahead Adder G=X and Y P=X xor Y G P G P G P G P G P G P G P G P Bitvis AND and or Bitvis OR or and Bitvis XOR xor and b23 b23 b22 b22 b21 b21 b20 b20 b3 b3 b2 b2 b1 b1 b0 b0 Barrel-shifter (se bilaga 6) shifter CO CARRY SUM b23 b23:21 b20:18 b5:3 M0 b2:0 C0 MUX1 X"000000" M1 MUX2 = Bergerkodsgenerator 5-bits bergerkod 2-bits xor 0 s counter 4-bits adder 4-bits 2-bits 0 s counter 4-bits adder ADDV or SUBV and 4-bits 3-bits 2-bits Ki 0 s counter 2-bits adder 2-bits 0 s counter b28:24 b23:0 M3 TRAP b23 BEQ RFT or and X" " 1 29-bits and X" " 0 BNE M2 MUX3 Bergerkodsgenerator 5-bits bergerkod b23:21 2-bits 0 s counter 4-bits adder 4-bits b20:18 2-bits 0 s counter 4-bits adder 4-bits 3-bits b5:3 2-bits 0 s counter 2-bits adder b2:0 2-bits 0 s counter Ki MUX1 OP-decode MUX2 MUX3 Illegal instruction and xor b6 b6 b5 b5 D Q D0 S R D Q D1 S R D Q D2 S R D Q D3 S R D Q D4 S R D Q D5 S R D Q D6 S R D Q D7 S R D Q D8 S R D Q D9 S R D Q D10 S R D Q D11 S R D Q D12 SR D Q D13 S R D Q D14 S R PULSEout CO OV TRAP K QC Q ALU_DATA CC XC YC OPout FAILUREBUSout NEXTOPout D_DESTout A_DESTout ALU_ADDR 51
52 Bilaga 5 BC-steget D Q D0 FAILUREBUSout S R D Q D1 PULSEout S R D Q D2 TRAPout S R D Q D3 OVout S R D Q D4 OPout berger_in berger_ex B2Fin FAILUREBUSin & b7 b7 C0 = B1F & b8 b8 S R D Q D5 S R NEXTOPout PULSEin TRAPin OVin D Q D6 SR RESout OP NEXTOPin RESin D Q D7 S R D_DESTout D_DESTin A_DESTin CLK D Q D8 S R A_DESTout RESET clear_reg OR clear_reg2 52
53 CLK Bilaga 6 WB-steget RESET clear_reg clear_reg2 PULSEin reg_disable FAILUREBUSin A_DESTin NEXTOPin OP DATA_IOin D_DESTin RESin OR "011111" TRAP = = = C0 C1 C2 SW LW PUT PRT OTHERS and and OP-decode or b9 RW PRI WEinv OEinv WB_failure C3 D0 " " S Q RW PRI WEinv OEinv or OEinv or or WEinv = R b19:0 ADDR_DM disable b29:0 DATA_DM and and OP M0 D Q D1 S R D Q D2 S R D Q D3 S R D Q D4 S R D Q D5 S R D Q D6 S R D Q D7 S R D Q S R D8 D Q D9 S R A_DESTout PULSEout FAILUREBUSout DISABLE IO_RW PRI D_DESTout DATA_IOout IOPRI IODDR 53
54 Bilaga 7 Felhanteraren! " # " $% & " 54
55 Bilaga 8 Skifter ')( -/. 0/1 +,! * +, "$#% & & 55
56 Bilaga 9 BP-blocket % -!BA -!BC,B& 0 1 & 1 % # DB& )-! % -!A -! E F && > > 0 9 &! "!# $! % % '&)( * +!, +!'% *- % -.! '! / -! :1 3 3 ; <=<+ > 1 1 >? & > 3 1 > & > 13 > > 3 1 > > 1 1 >?& > 1 1 > > 1 1 > ; <=<
57 Bilaga 10 Assemblatorn ASRC Vid konstruktionsarbetet av processorn utvecklades en enkel assemblator för att underlätta skapandet av testprogram och applikationsprogram. Assemblatorn kallas ASRC (Assemble SouRCe). ASRC är ett DOS-program som tar emot en fil med kod (filnamn.asm), assemblerar den och skapar ett VHDL-ROM i en annan fil (filnamn.vhd). Detta VHDL-ROM är helt kompatibelt med processorn. Assemblatorn kan även skapa en scriptfil som är kompatibel med det utvecklingssystem som användes vid konstruktion av prototypsystemet. Syntax: ASRC [-v][-b][-s] filnamn.asm Där flaggorna, -v genererar VHDL-ROM i filen filnamn.vhd -b genererar script-fil i filen filnamn.scr -s genererar VHDL-ROM i filen filnamn.vhd samt skriver ut programmet i DOSprompten Ingen flagga genererar VHDL-ROM i filen finlamn.vhd med en sökväg som anges i filen conf.dat. Filen conf.dat innehåller följande data: -CRC-polynom som används för beräkning av PCS (I detta fall ) -Storlek hos det genererade VHDL-ROM:et (I detta fall 1024 bytes ) -Sökväg till designbibliotek Sökvägen används för att det ska vara enkelt att skriva ett program i en texteditor och sedan med ett WINDOWS makro direkt kunna assemblera och infoga det nya ROM:et i designen. ASRC kan hitta syntaxfel i programmet, upptäcker om register används som inte finns (>R31) och om programmet kräver större utrymme än (det i conf.dat ) angivna ROM:ets storlek. Om ASRC hittar ett fel skrivs detta ut tillsammans med radnummer varför flaggan [-s] kan vara användbar. Alla program som skrivs assembleras måste avslutas med instruktionen END så att assemblatorn ska förstå att programmet är slut. Instruktionen END översätts till en NOP i VHDL-ROM:et 57
58 Bilaga 11 Applikation Som demonstrationsapplikation byggdes ett 2-handsmanöverdon av typ III. Typ III innebär synkron påverkan av manöverdonen inom 0,5 s (dvs. tidsfördröjningen 0,5 s). Typ III kräver dessutom att båda manöverdonen släppts innan maskinen kan återstartas. Mjukvara Styrprogrammet till 2-handsmanövern kan ses som en tillståndsmaskin, se figur (48(<!= 1 2 )!48( & % 48( 132 (48(,<!= 1 2 )!48( '48(<!= 2 48( '45$9!:7; 2 45! "$# /Q5! "$# ' ' (,9!:7; 2 48( % '& 0 :A9!BBC( :A9!BB,) 132 (C4 1EDFD ;!G79H IKJL= M!:C& DONP ( 132 )4 1EDFD ;!G79H IKJL= M!:C& DONP ) % 1 ' )+*,# 1 2 (45$<!= 132 )!48( -/ ( '6(7"+*,# 1 2 (45$<!= 1 2 )! (48(,9!:7; 1 2 )!45 % '& 3) % >'? ' )+*,# '45$<!= (48(<!= 132 )!48( Figur 10: Styrprogrammets tillståndsmaskin Vid uppstart lägger sig programmet i IDLE och väntar på att någon av startknapparna trycks ner. Om någon knapp aktiveras övergår programmet till WAIT 0,5 s och väntar i 0,5 s på att den andra knappen ska tryckas ner. Om inte så sker går programmet till WAIT A=B=0 och väntar på att båda startknapparna är släppta innan det återgår till IDLE. Om däremot den andra knappen aktiveras inom 0,5 s går styrprogrammet till START1 och ena reläet aktiveras. Programmet väntar sedan i 20ms innan det kontrollerar att feedbacksignalen från reläet kommer. Därefter aktiveras det andra reläet, START2, och dess feedbacksignal kontrolleras. Vid stopp, dvs. att någon knapp släppts, går programmet via WAIT A=B=0 tillbaka till IDLE för att säkerställa att ingen av startknapparna är aktiverade. I alla tillstånd kontrolleras även statusbitarna för insignalerna för att verifiera att knapparna ger rätt signaler. För assemblerkod se bilaga
59 Hårdvara Båda knapparna i uppkopplingen är 2-poliga och ger vardera två separata och relativt varandra inverterade signaler. Signalerna är i sin tur kopplade till varsin IO-port. IOportarna är konfigurerade med prioritet 0 så att ingångarna för startknapparna kräver att polerna från startknapparna ska vara inverterade. Utgångarna från IO-portarna som startar maskinen är kopplade via en förstärkare till ett relä var. Reläerna är 2-poliga där en pol är kopplad till maskinen den styr och den andra ger en feedbacksignal som går hög om reläet är draget. Varje feedbacksignal är kopplad till ett bitpar på IO-portarna som då är konfigurerade med prioritet 1 dvs. båda ingångarna måste vara lika. Vid ett eventuellt fel i exekveringen av styrprogrammet som gör att processorn sätts i feltyst räcker det med att en av IO-portarna nollställs för att maskinen ska stanna. För uppkoppling se figur 11. " " '%&& " " " " '(&& " " #%$& )* + "! " " #%$& )* + "! " " Figur 11: Uppkoppling av hårdvara. 59
60 Bilaga 12 Assemblerkod för styrprogrammet. BEQ R0 R0 6 'jump to initilize' ADDX R30 R0 12 'traphandler - t = 15ms' NOP BNE R30 R0-2 'loop untill t=0' ADDI R30 R30-1 'countdown t' NOP RFT R31 R0 0 'return from trap' NOP ADDI R1 RO 4079 'initilize - set start1-out mask' ADDI R2 RO 4063 'set start2-out mask' ADDI R3 RO 4047 'set stop-out mask' ADDI R4 R 'IO DDR= IN=0 OUT=1' PRT R4 R0 12 'IO PRI=-1100 OR=0 AND=1' PUT R0 R0 0 'Set all outputs to 0' NOP 'idle' RIO R5 R0 0 'read IO port' TRP NOP NOP ANDI R6 R5 12 'check 3,4 - FB1 and FB2' BNE R6 R0 73 'jump to safe if FB1=1 or FB2=1' ANDI R6 R5 3 'check 1,2 - button A and B' NOP BNE R6 R0 3 'jump to wait 0,5s if A or B set' NOP NOP BEQ R0 R0-13 'loop idle' NOP ADDI R7 R0 30 'wait for 0.5 sec' NOP RIO R5 R0 0 'read IO port' TRP NOP ADDI R7 R7-1 ANDI R6 R5 12 'check 3,4 - FB1 and FB2' BNE R6 R0 58 'jump to safe if FB1=1 or FB2=1' ANDI R6 R5 3 'check 1,2 - button A and B' ADDI R8 R0 3 'mask button A and B' BEQ R8 R6 18 'jump to start1 if A=B=1' NOP NOP BNE R7 R0-13 'loop wait for 0.5 sec' NOP NOP 'wait for A=B=0' RIO R5 R0 0 'read IO port' TRP NOP NOP ANDI R6 R5 12 'check 3,4 - FB1 and FB2' BNE R6 R0 44 'jump to safe if FB1=1 or FB2=1' ANDI R6 R5 3 'check 1,2 - button A and B' NOP BEQ R6 R0-39 'jump to idle if A=B=0' NOP NOP 60
61 BEQ R0 R0-13 NOP NOP PUT R1 R0 16 TRP NOP NOP RIO R5 R0 0 NOP NOP ADDI R8 R0 4 ANDI R6 R5 12 BNE R6 R8 26 NOP NOP PUT R2 R0 48 TRP NOP NOP RIO R5 R0 0 TRP NOP ADDI R8 R0 12 ANDI R6 R5 12 BNE R6 R8 14 ANDI R6 R5 3 ADDI R8 R0 3 BNE R6 R8 4 NOP NOP BEQ R0 R0-13 NOP NOP PUT R3 R0 0 TRP NOP NOP BEQ R0 R0-50 NOP NOP PUT R3 R0 0 SFE R0 R0 0 BEQ R0 R0-1 END 'loop wait for A=B=0' 'start1' 'read IO port' 'mask FB1' 'check 3,4 - FB1 and FB2' 'jump to safe if FB1=0 or FB2=1' 'start2' 'check A=0 or B=0' 'read IO port' 'mask FB1' 'check 3,4 - FB1 and FB2' 'jump to safe if FB1=0 or FB2=0' 'check 1,2 - button A and B' 'mask button A and B' 'jump to stop' 'loop check A=0 or B=0' 'stop' 'jump to wait for A=0 and B=0' 'safe-state' 61
62 Bilaga 13 VHDL-kod för Krets 1 Title : KRETS1 Design : xjobb Author : - Company : SP File : KRETS1.vhd Version : 1.0 Date : Rev. by. : Description : Sammankoppling av blocken i krets 1 library IEEE; use IEEE.std_logic_1164.all; entity KRETS1 is port( B2F_IN : in STD_LOGIC; CLK : in STD_LOGIC; DISABLE2 : in STD_LOGIC; HW_TRAP : in STD_LOGIC; PULSE_IN : in STD_LOGIC; RESET : in STD_LOGIC; RETRY2 : in STD_LOGIC; SAFE2 : in STD_LOGIC; BERGERIN : in STD_LOGIC_VECTOR (4 downto 0 DATA_DM_in : in STD_LOGIC_VECTOR (31 downto 0 IM_DATA : in STD_LOGIC_VECTOR (63 downto 0 RESET_BUS2 : in STD_LOGIC_VECTOR (4 downto 0 CO : out STD_LOGIC; K : out STD_LOGIC; io_select : out STD_LOGIC; io_wr : out STD_LOGIC; OEinv : out STD_LOGIC; PULSE : out STD_LOGIC; TST : out STD_LOGIC; WEinv : out STD_LOGIC; end KRETS1; conf_ddr : out STD_LOGIC; CC : out STD_LOGIC_VECTOR (4 downto 0 DM_ADDR : out STD_LOGIC_VECTOR (19 downto 0 DM_DATA_out : out STD_LOGIC_VECTOR (31 downto 0 FAILUREBUS : out STD_LOGIC_VECTOR (13 downto 0 OP : out STD_LOGIC_VECTOR (4 downto 0 QC : out STD_LOGIC_VECTOR (4 downto 0 XC : out STD_LOGIC_VECTOR (4 downto 0 YC : out STD_LOGIC_VECTOR (4 downto 0 IM_ADDR : buffer STD_LOGIC_VECTOR (15 downto 0 IO_A : inout STD_LOGIC_VECTOR (11 downto 0 IO_B : inout STD_LOGIC_VECTOR (11 downto 0) architecture KRETS1 of KRETS1 is signal FAILUREX : STD_LOGIC_VECTOR (13 downto 0 signal ITST : STD_LOGIC ; signal BUS142 : STD_LOGIC_VECTOR (28 downto 0 signal BUS148 : STD_LOGIC_VECTOR (11 downto 0 signal BUS177 : STD_LOGIC_VECTOR (4 downto 0 62
63 signal BUS71 : STD_LOGIC_VECTOR (11 downto 0 signal BUS77 : STD_LOGIC_VECTOR (11 downto 0 signal BUS89 : STD_LOGIC_VECTOR (11 downto 0 signal BUS98 : STD_LOGIC_VECTOR (11 downto 0 signal NET128 : STD_LOGIC ; signal NET158 : STD_LOGIC ; signal NET165 : STD_LOGIC ; signal NET169 : STD_LOGIC ; signal NET509 : STD_LOGIC ; signal NET802 : STD_LOGIC ; component CPU port ( B2F_IN : in STD_LOGIC; BERGERIN : in STD_LOGIC_VECTOR (4 downto 0 CLEAR_REG : in STD_LOGIC_VECTOR (4 downto 0 CLEAR_REG2 : in STD_LOGIC_VECTOR (4 downto 0 DATA_DM_in : in STD_LOGIC_VECTOR (31 downto 0 DISABLE : in STD_LOGIC; DISABLE2 : in STD_LOGIC; HW_TRAP : in STD_LOGIC; reg_disable : in STD_LOGIC; IO_DATA_IN : in STD_LOGIC_VECTOR (28 downto 0 RETRY : in STD_LOGIC; RETRY2 : in STD_LOGIC; ROM_DATA : in STD_LOGIC_VECTOR (63 downto 0 SAFE : in STD_LOGIC; SAFE2 : in STD_LOGIC; clk : in STD_LOGIC; reset : in STD_LOGIC; ADDR_DM : out STD_LOGIC_VECTOR (19 downto 0 CC : out STD_LOGIC_VECTOR (4 downto 0 CO : out STD_LOGIC; io_select : out STD_LOGIC; io_wr : out STD_LOGIC; DATA_DM_out : out STD_LOGIC_VECTOR (31 downto 0 FAILUREBUS : out STD_LOGIC_VECTOR (13 downto 0 IO_DATA_OUT : out STD_LOGIC_VECTOR (11 downto 0 IO_DDR : out STD_LOGIC_VECTOR (11 downto 0 IO_PRI : out STD_LOGIC_VECTOR (11 downto 0 IO_RW : out STD_LOGIC; K : out STD_LOGIC; OEinv : out STD_LOGIC; OP : out STD_LOGIC_VECTOR (4 downto 0 PRI : out STD_LOGIC; PULSE_OUT : out STD_LOGIC; QC : out STD_LOGIC_VECTOR (4 downto 0 TST : out STD_LOGIC; WEinv : out STD_LOGIC; XC : out STD_LOGIC_VECTOR (4 downto 0 YC : out STD_LOGIC_VECTOR (4 downto 0 ROM_ADDR : buffer STD_LOGIC_VECTOR (15 downto 0) end component ; component FAULT port ( TST : in STD_LOGIC; clk : in STD_LOGIC; failure_bus : in STD_LOGIC_VECTOR (13 downto 0 reset : in STD_LOGIC; reg_disable : out STD_LOGIC; reset_bus : out STD_LOGIC_VECTOR (4 downto 0 retry : out STD_LOGIC; safe : out STD_LOGIC end component ; component IO_CMP port ( 63
64 IOa : in STD_LOGIC_VECTOR (11 downto 0 IOb : in STD_LOGIC_VECTOR (11 downto 0 priority : in STD_LOGIC_VECTOR (11 downto 0 reset : in STD_LOGIC; set_pri : in STD_LOGIC; IO_in : out STD_LOGIC_VECTOR (28 downto 0) end component ; component IOPORT port ( DDR : in STD_LOGIC_VECTOR (11 downto 0 IO_out : in STD_LOGIC_VECTOR (11 downto 0 RW : in STD_LOGIC; reset : in STD_LOGIC; safe_state : in STD_LOGIC; safe_state2 : in STD_LOGIC; safe_state3 : in STD_LOGIC; use_io : in STD_LOGIC; IO_in : out STD_LOGIC_VECTOR (11 downto 0 IO_port : inout STD_LOGIC_VECTOR (11 downto 0) end component ; component IOPORTB port ( DDR : in STD_LOGIC_VECTOR (11 downto 0 IO_out : in STD_LOGIC_VECTOR (11 downto 0 RW : in STD_LOGIC; reset : in STD_LOGIC; safe_state : in STD_LOGIC; safe_state2 : in STD_LOGIC; safe_state3 : in STD_LOGIC; use_io : in STD_LOGIC; IO_in : out STD_LOGIC_VECTOR (11 downto 0 conf_ddr : out STD_LOGIC; IO_port : inout STD_LOGIC_VECTOR (11 downto 0) end component ; component PULSE_COUNTER port ( clk : in STD_LOGIC; pulse : in STD_LOGIC; reset : in STD_LOGIC; safe_state : out STD_LOGIC end component ; for U0 : CPU use entity work.cpu(cpu_arch U0 : CPU port map( ADDR_DM => DM_ADDR, B2F_IN => B2F_IN, BERGERIN => BERGERIN, CC => CC, CLEAR_REG => BUS177, CLEAR_REG2 => RESET_BUS2, CO => CO, DATA_DM_in => DATA_DM_in, DATA_DM_out => DM_DATA_out, DISABLE => NET165, DISABLE2 => DISABLE2, FAILUREBUS => FAILUREX, HW_TRAP => HW_TRAP, IO_DATA_IN => BUS142, IO_DATA_OUT => BUS89, 64
65 IO_DDR => BUS98, IO_PRI => BUS148, IO_RW => NET128, io_select => io_select, io_wr => io_wr, K => K, OEinv => OEinv, OP => OP, PRI => NET158, PULSE_OUT => PULSE, QC => QC, RETRY => NET169, RETRY2 => RETRY2, ROM_ADDR => IM_ADDR, ROM_DATA => IM_DATA, SAFE => NET509, SAFE2 => SAFE2, TST => itst, WEinv => WEinv, XC => XC, YC => YC, clk => CLK, reset => RESET U1 : FAULT port map( TST => itst, clk => CLK, failure_bus => FAILUREX, reg_disable => NET165, reset => RESET, reset_bus => BUS177, retry => NET169, safe => NET509 U2 : IOPORT port map( DDR => BUS98, IO_in => BUS77, IO_out => BUS89, IO_port => IO_A, RW => NET128, reset => RESET, safe_state => NET509, safe_state2 => SAFE2, safe_state3 => NET802, use_io => NET158 U3 : IO_CMP port map( IO_in => BUS142, IOa => BUS71, IOb => BUS77, priority => BUS148, reset => RESET, set_pri => NET158 U4 : IOPORTB port map( DDR => BUS98, IO_in => BUS71, IO_out => BUS89, IO_port => IO_B, RW => NET128, conf_ddr => conf_ddr, reset => RESET, 65
66 safe_state => NET509, safe_state2 => SAFE2, safe_state3 => NET802, use_io => NET158 U5 : PULSE_COUNTER port map( clk => CLK, pulse => PULSE_IN, reset => RESET, safe_state => NET802 FAILUREBUS <= FAILUREX; TST <= itst; end KRETS1; Title : CPU Design : xjobb Author : - Company : SP File : cpu.vhd Version : 1.0 Date : Rev. by. : Description : Sammankoppling av blocken i cpu:n library IEEE; use IEEE.std_logic_1164.all; entity CPU is port( B2F_IN : in STD_LOGIC; DISABLE : in STD_LOGIC; DISABLE2 : in STD_LOGIC; HW_TRAP : in STD_LOGIC; RETRY : in STD_LOGIC; RETRY2 : in STD_LOGIC; SAFE : in STD_LOGIC; SAFE2 : in STD_LOGIC; clk : in STD_LOGIC; reset : in STD_LOGIC; BERGERIN : in STD_LOGIC_VECTOR (4 downto 0 CLEAR_REG : in STD_LOGIC_VECTOR (4 downto 0 CLEAR_REG2 : in STD_LOGIC_VECTOR (4 downto 0 DATA_DM_in : in STD_LOGIC_VECTOR (31 downto 0 IO_DATA_IN : in STD_LOGIC_VECTOR (28 downto 0 ROM_DATA : in STD_LOGIC_VECTOR (63 downto 0 CO : out STD_LOGIC; io_select : out STD_LOGIC; io_wr : out STD_LOGIC; IO_RW : out STD_LOGIC; K : out STD_LOGIC; OEinv : out STD_LOGIC; PRI : out STD_LOGIC; 66
67 PULSE_OUT : out STD_LOGIC; TST : out STD_LOGIC; WEinv : out STD_LOGIC; ADDR_DM : out STD_LOGIC_VECTOR (19 downto 0 CC : out STD_LOGIC_VECTOR (4 downto 0 DATA_DM_out : out STD_LOGIC_VECTOR (31 downto 0 FAILUREBUS : out STD_LOGIC_VECTOR (13 downto 0 IO_DATA_OUT : out STD_LOGIC_VECTOR (11 downto 0 IO_DDR : out STD_LOGIC_VECTOR (11 downto 0 IO_PRI : out STD_LOGIC_VECTOR (11 downto 0 OP : out STD_LOGIC_VECTOR (4 downto 0 QC : out STD_LOGIC_VECTOR (4 downto 0 XC : out STD_LOGIC_VECTOR (4 downto 0 YC : out STD_LOGIC_VECTOR (4 downto 0 ROM_ADDR : buffer STD_LOGIC_VECTOR (15 downto 0) end CPU; architecture CPU_arch of CPU is signal OPX : STD_LOGIC_VECTOR (4 downto 0 signal QCX : STD_LOGIC_VECTOR (4 downto 0 signal RES_BP : STD_LOGIC_VECTOR (31 downto 0 signal BUS100 : STD_LOGIC_VECTOR (5 downto 0 signal BUS104 : STD_LOGIC_VECTOR (28 downto 0 signal BUS108 : STD_LOGIC_VECTOR (13 downto 0 signal BUS112 : STD_LOGIC_VECTOR (13 downto 0 signal BUS116 : STD_LOGIC_VECTOR (12 downto 0 signal BUS1777 : STD_LOGIC_VECTOR (4 downto 0 signal BUS1783 : STD_LOGIC_VECTOR (5 downto 0 signal BUS4247 : STD_LOGIC_VECTOR (3 downto 0 signal BUS4251 : STD_LOGIC_VECTOR (1 downto 0 signal BUS4255 : STD_LOGIC_VECTOR (1 downto 0 signal BUS4259 : STD_LOGIC_VECTOR (1 downto 0 signal BUS4263 : STD_LOGIC_VECTOR (1 downto 0 signal BUS48 : STD_LOGIC_VECTOR (12 downto 0 signal BUS52 : STD_LOGIC_VECTOR (1 downto 0 signal BUS56 : STD_LOGIC_VECTOR (4 downto 0 signal BUS60 : STD_LOGIC_VECTOR (4 downto 0 signal BUS64 : STD_LOGIC_VECTOR (4 downto 0 signal BUS665 : STD_LOGIC_VECTOR (13 downto 0 signal BUS669 : STD_LOGIC_VECTOR (13 downto 0 signal BUS68 : STD_LOGIC_VECTOR (4 downto 0 signal BUS681 : STD_LOGIC_VECTOR (4 downto 0 signal BUS693 : STD_LOGIC_VECTOR (28 downto 0 signal BUS697 : STD_LOGIC_VECTOR (4 downto 0 signal BUS701 : STD_LOGIC_VECTOR (4 downto 0 signal BUS713 : STD_LOGIC_VECTOR (28 downto 0 signal BUS717 : STD_LOGIC_VECTOR (5 downto 0 signal BUS72 : STD_LOGIC_VECTOR (4 downto 0 signal BUS725 : STD_LOGIC_VECTOR (31 downto 0 signal BUS741 : STD_LOGIC_VECTOR (5 downto 0 signal BUS756 : STD_LOGIC_VECTOR (31 downto 0 signal BUS76 : STD_LOGIC_VECTOR (4 downto 0 signal BUS84 : STD_LOGIC_VECTOR (4 downto 0 signal BUS88 : STD_LOGIC_VECTOR (4 downto 0 signal BUS92 : STD_LOGIC_VECTOR (28 downto 0 signal BUS96 : STD_LOGIC_VECTOR (28 downto 0 signal NET124 : STD_LOGIC ; signal NET132 : STD_LOGIC ; signal NET162 : STD_LOGIC ; signal NET166 : STD_LOGIC ; signal NET170 : STD_LOGIC ; signal NET174 : STD_LOGIC ; signal NET3529 : STD_LOGIC ; signal NET4558 : STD_LOGIC ; signal NET4562 : STD_LOGIC ; signal NET4842 : STD_LOGIC ; signal NET641 : STD_LOGIC ; signal NET645 : STD_LOGIC ; 67
68 signal NET649 : STD_LOGIC ; signal NET653 : STD_LOGIC ; signal NET657 : STD_LOGIC ; signal NET661 : STD_LOGIC ; signal i_ex_trap : std_logic; component BP port ( TSTin : in STD_LOGIC; a_dest_in : in STD_LOGIC_VECTOR (5 downto 0 b2f_in : in STD_LOGIC; berger_ex : in STD_LOGIC_VECTOR (4 downto 0 berger_in : in STD_LOGIC_VECTOR (4 downto 0 clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; clk : in STD_LOGIC; d_dest_in : in STD_LOGIC_VECTOR (28 downto 0 f_bus_in : in STD_LOGIC_VECTOR (13 downto 0 nop_in : in STD_LOGIC_VECTOR (4 downto 0 op_in : in STD_LOGIC_VECTOR (4 downto 0 ov_in : in STD_LOGIC; pulse_in : in STD_LOGIC; res_in : in STD_LOGIC_VECTOR (31 downto 0 reset : in STD_LOGIC; trap_in : in STD_LOGIC; wb_tag : in STD_LOGIC_VECTOR (1 downto 0 O_wb_tag : out STD_LOGIC_VECTOR (1 downto 0 TSTout : out STD_LOGIC; a_dest_out : out STD_LOGIC_VECTOR (5 downto 0 d_dest_out : out STD_LOGIC_VECTOR (28 downto 0 f_bus_out : out STD_LOGIC_VECTOR (13 downto 0 nop_out : out STD_LOGIC_VECTOR (4 downto 0 op_out : out STD_LOGIC_VECTOR (4 downto 0 ov_out : out STD_LOGIC; pulse_out : out STD_LOGIC; res_out : out STD_LOGIC_VECTOR (31 downto 0 trap_out : out STD_LOGIC end component ; component EX port ( A_DESTin : in STD_LOGIC_VECTOR (5 downto 0 CLK : in STD_LOGIC; D_DESTin : in STD_LOGIC_VECTOR (28 downto 0 NEXTOPin : in STD_LOGIC_VECTOR (4 downto 0 OP : in STD_LOGIC_VECTOR (4 downto 0 RST : in STD_LOGIC; TSTin : in STD_LOGIC; X : in STD_LOGIC_VECTOR (28 downto 0 Y : in STD_LOGIC_VECTOR (28 downto 0 clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; failure_bus_in : in STD_LOGIC_VECTOR (13 downto 0 pulse_in : in STD_LOGIC; wb_tag : in STD_LOGIC_VECTOR (1 downto 0 ALU_ADDR : out STD_LOGIC_VECTOR (5 downto 0 ALU_DATA : out STD_LOGIC_VECTOR (31 downto 0 A_DESTout : out STD_LOGIC_VECTOR (5 downto 0 CC : out STD_LOGIC_VECTOR (4 downto 0 CO : out STD_LOGIC; D_DESTout : out STD_LOGIC_VECTOR (28 downto 0 K : out STD_LOGIC; NEXTOPout : out STD_LOGIC_VECTOR (4 downto 0 OPout : out STD_LOGIC_VECTOR (4 downto 0 OV : out STD_LOGIC; O_wb_tag : out STD_LOGIC_VECTOR (1 downto 0 Q : out STD_LOGIC_VECTOR (31 downto 0 QC : out STD_LOGIC_VECTOR (4 downto 0 TRAP : out STD_LOGIC; 68
69 TSTout : out STD_LOGIC; XC : out STD_LOGIC_VECTOR (4 downto 0 YC : out STD_LOGIC_VECTOR (4 downto 0 failure_bus : out STD_LOGIC_VECTOR (13 downto 0 pulse_out : out STD_LOGIC end component ; component IF_STAGE port ( HW_TRAP : in STD_LOGIC; NEXT_PC : in STD_LOGIC_VECTOR (12 downto 0 ROM_data : in STD_LOGIC_VECTOR (63 downto 0 branch_taken : in STD_LOGIC; clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; clk : in STD_LOGIC; reset : in STD_LOGIC; retry : in STD_LOGIC; ex_trap : in std_logic; retry2 : in STD_LOGIC; safe : in STD_LOGIC; safe2 : in STD_LOGIC; trap_busy : in STD_LOGIC; NOP : out STD_LOGIC_VECTOR (4 downto 0 OP : out STD_LOGIC_VECTOR (4 downto 0 PC : out STD_LOGIC_VECTOR (12 downto 0 addr2 : out STD_LOGIC_VECTOR (4 downto 0 addr_mode : out STD_LOGIC_VECTOR (1 downto 0 berger_code : out STD_LOGIC_VECTOR (4 downto 0 dest : out STD_LOGIC_VECTOR (4 downto 0 failure_bus : out STD_LOGIC_VECTOR (13 downto 0 hw_trap_out : out STD_LOGIC; imm_ximm_tag : out STD_LOGIC_VECTOR (3 downto 0 pulse_out : out STD_LOGIC; src1 : out STD_LOGIC_VECTOR (4 downto 0 src2 : out STD_LOGIC_VECTOR (11 downto 0 trap_retry : out STD_LOGIC; wb_tag : out STD_LOGIC_VECTOR (1 downto 0 ROM_ADDR : buffer STD_LOGIC_VECTOR (15 downto 0) end component ; component READ_REG port ( CLK : in STD_LOGIC; PC : in STD_LOGIC_VECTOR (12 downto 0 RESET : in STD_LOGIC; addr2 : in STD_LOGIC_VECTOR (4 downto 0 addr_mode : in STD_LOGIC_VECTOR (1 downto 0 alu_addr : in STD_LOGIC_VECTOR (5 downto 0 reg_disable : in std_logic; alu_addr2 : in STD_LOGIC_VECTOR (5 downto 0 alu_data : in STD_LOGIC_VECTOR (31 downto 0 alu_data2 : in STD_LOGIC_VECTOR (31 downto 0 berger_code : in STD_LOGIC_VECTOR (4 downto 0 bp_addr : in STD_LOGIC_VECTOR (5 downto 0 bp_data : in STD_LOGIC_VECTOR (31 downto 0 clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; dest : in STD_LOGIC_VECTOR (4 downto 0 failure_bus_in : in STD_LOGIC_VECTOR (13 downto 0 i_check : in STD_LOGIC; imm_xim_tag : in STD_LOGIC_VECTOR (3 downto 0 in_pulse : in STD_LOGIC; nopcode : in STD_LOGIC_VECTOR (4 downto 0 opcode : in STD_LOGIC_VECTOR (4 downto 0 69
70 src1 : in STD_LOGIC_VECTOR (4 downto 0 src2 : in STD_LOGIC_VECTOR (11 downto 0 trap_retry : in STD_LOGIC; wb_tag : in STD_LOGIC_VECTOR (1 downto 0 write_addr : in STD_LOGIC_VECTOR (4 downto 0 write_data : in STD_LOGIC_VECTOR (31 downto 0 O_wb_tag : out STD_LOGIC_VECTOR (1 downto 0 TSTout : out STD_LOGIC; branch_taken : out STD_LOGIC; failure_bus : out STD_LOGIC_VECTOR (13 downto 0 o_ddest : out STD_LOGIC_VECTOR (28 downto 0 o_next_pc : out STD_LOGIC_VECTOR (12 downto 0 o_rdest : out STD_LOGIC_VECTOR (5 downto 0 o_data1 : out STD_LOGIC_VECTOR (28 downto 0 o_data2 : out STD_LOGIC_VECTOR (28 downto 0 o_nopcode : out STD_LOGIC_VECTOR (4 downto 0 o_opcode : out STD_LOGIC_VECTOR (4 downto 0 out_pulse : out STD_LOGIC; trap_out : out STD_LOGIC end component ; component WB port ( A_DEST : in STD_LOGIC_VECTOR (5 downto 0 CLK : in STD_LOGIC; DATA_DM_in : in STD_LOGIC_VECTOR (31 downto 0 DATA_IOin : in STD_LOGIC_VECTOR (28 downto 0 D_DEST : in STD_LOGIC_VECTOR (28 downto 0 NEXTOP : in STD_LOGIC_VECTOR (4 downto 0 OP : in STD_LOGIC_VECTOR (4 downto 0 OV : in STD_LOGIC; RES : in STD_LOGIC_VECTOR (28 downto 0 RST : in STD_LOGIC; TRAP : in STD_LOGIC; TSTin : in STD_LOGIC; clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; failure_bus_in : in STD_LOGIC_VECTOR (13 downto 0 pulse_in : in STD_LOGIC; reg_disable : in STD_LOGIC; reg_disable2 : in STD_LOGIC; wb_tag : in STD_LOGIC_VECTOR (1 downto 0 io_select : out STD_LOGIC; io_wr : out STD_LOGIC; ADDR_DM : out STD_LOGIC_VECTOR (19 downto 0 A_DESTout : out STD_LOGIC_VECTOR (4 downto 0 DATA_DM_out : out STD_LOGIC_VECTOR (31 downto 0 DATA_IOout : out STD_LOGIC_VECTOR (11 downto 0 D_DESTout : out STD_LOGIC_VECTOR (31 downto 0 IODDR : out STD_LOGIC_VECTOR (11 downto 0 IOPRI : out STD_LOGIC_VECTOR (11 downto 0 IO_RW : out STD_LOGIC; OEinv : out STD_LOGIC; PRI : out STD_LOGIC; TSTout : out STD_LOGIC; WEinv : out STD_LOGIC; failure_bus : out STD_LOGIC_VECTOR (13 downto 0 pulse_out : out STD_LOGIC; ex_trap : out STD_lOGIC; disable : buffer STD_LOGIC end component ; 70
71 U0 : IF_STAGE port map( HW_TRAP => HW_TRAP, NEXT_PC => BUS116, NOP => BUS60, OP => BUS56, PC => BUS48, ex_trap => i_ex_trap, ROM_ADDR => ROM_ADDR, ROM_data => ROM_DATA, addr2 => BUS72, addr_mode => BUS52, berger_code => BUS80, branch_taken => NET124, clear_reg => CLEAR_REG(0), clear_reg2 => CLEAR_REG2(0), clk => clk, dest => BUS64, failure_bus => BUS112, hw_trap_out => NET162, imm_ximm_tag => BUS4247, pulse_out => NET170, reset => reset, retry => RETRY, retry2 => RETRY2, safe => SAFE, safe2 => SAFE2, src1 => BUS68, src2 => BUS76, trap_busy => NET132, trap_retry => NET166, wb_tag => BUS4251 U1 : READ_REG port map( CLK => clk, O_wb_tag => BUS4255, PC => BUS48, RESET => reset, TSTout => NET4842, addr2 => BUS72, addr_mode => BUS52, reg_disable => DISABLE2, alu_addr => BUS717, alu_addr2 => BUS741, alu_data => BUS725, alu_data2 => BUS756, berger_code => BUS80, bp_addr => BUS1942, bp_data => res_bp, branch_taken => NET124, clear_reg => CLEAR_REG(1), clear_reg2 => CLEAR_REG2(1), dest => BUS64, failure_bus => BUS108, failure_bus_in => BUS112, i_check => NET3529, imm_xim_tag => BUS4247, in_pulse => NET170, nopcode => BUS60, o_ddest => BUS104, o_next_pc => BUS116, o_rdest => BUS100, o_data1 => BUS92, o_data2 => BUS96, o_nopcode => BUS88, o_opcode => BUS84, opcode => BUS56, 71
72 out_pulse => NET174, src1 => BUS68, src2 => BUS76, trap_out => NET132, trap_retry => NET166, wb_tag => BUS4251, write_addr => BUS1777, write_data => BUS1783 U2 : EX port map( ALU_ADDR => BUS717, ALU_DATA => BUS725, A_DESTin => BUS100, A_DESTout => BUS741, CC => CC, CLK => clk, CO => CO, D_DESTin => BUS104, D_DESTout => BUS693, K => K, NEXTOPin => BUS88, NEXTOPout => BUS681, OP => BUS84, OPout => OPX, OV => NET661, O_wb_tag => BUS4259, Q => BUS756, QC => QCX, RST => reset, TRAP => NET649, TSTin => NET4842, TSTout => NET4562, X => BUS92, XC => XC, Y => BUS96, YC => YC, clear_reg => CLEAR_REG(2), clear_reg2 => CLEAR_REG2(2), failure_bus => BUS665, failure_bus_in => BUS108, pulse_in => NET174, pulse_out => NET645, wb_tag => BUS4255 U3 : BP port map( O_wb_tag => BUS4263, TSTin => NET4562, TSTout => NET4558, a_dest_in => BUS741, a_dest_out => BUS1942, b2f_in => B2F_IN, berger_ex => QCX, berger_in => BERGERIN, clear_reg => CLEAR_REG(3), clear_reg2 => CLEAR_REG2(3), clk => clk, d_dest_in => BUS693, d_dest_out => BUS713, f_bus_in => BUS665, f_bus_out => BUS669, nop_in => BUS681, nop_out => BUS701, op_in => OPX, op_out => BUS697, ov_in => NET661, ov_out => NET657, 72
73 pulse_in => NET645, pulse_out => NET641, res_in => BUS756, res_out => res_bp, reset => reset, trap_in => NET649, trap_out => NET653, wb_tag => BUS4259 U4 : WB port map( ADDR_DM => ADDR_DM, A_DEST => BUS1942, A_DESTout => BUS1777, CLK => clk, ex_trap => i_ex_trap, DATA_DM_in => DATA_DM_in, DATA_DM_out => DATA_DM_out, DATA_IOin => IO_DATA_IN, DATA_IOout => IO_DATA_OUT, D_DEST => BUS713, D_DESTout => BUS1783, IODDR => IO_DDR, IOPRI => IO_PRI, IO_RW => IO_RW, io_select => io_select, io_wr => io_wr, NEXTOP => BUS701, OEinv => OEinv, OP => BUS697, OV => NET657, PRI => PRI, RES(0) => res_bp(0), RES(1) => res_bp(1), RES(2) => res_bp(2), RES(3) => res_bp(3), RES(4) => res_bp(4), RES(5) => res_bp(5), RES(6) => res_bp(6), RES(7) => res_bp(7), RES(8) => res_bp(8), RES(9) => res_bp(9), RES(10) => res_bp(10), RES(11) => res_bp(11), RES(12) => res_bp(12), RES(13) => res_bp(13), RES(14) => res_bp(14), RES(15) => res_bp(15), RES(16) => res_bp(16), RES(17) => res_bp(17), RES(18) => res_bp(18), RES(19) => res_bp(19), RES(20) => res_bp(20), RES(21) => res_bp(21), RES(22) => res_bp(22), RES(23) => res_bp(23), RES(24) => res_bp(24), RES(25) => res_bp(25), RES(26) => res_bp(26), RES(27) => res_bp(27), RES(28) => res_bp(28), RST => reset, TRAP => NET653, TSTin => NET4558, TSTout => TST, WEinv => WEinv, 73
74 clear_reg => CLEAR_REG(4), clear_reg2 => CLEAR_REG2(4), disable => NET3529, failure_bus => FAILUREBUS, failure_bus_in => BUS669, pulse_in => NET641, pulse_out => PULSE_OUT, reg_disable => DISABLE, reg_disable2 => DISABLE2, wb_tag => BUS4263 OP <= OPX; QC <= QCX; end CPU_arch; Title : IF-stage Design : xjobb Author : Andreas Söderberg Company : SP File : if-stage.vhd Version : 1.0 Date : Rev. by. : Description : Sammankoppling av blocken i Instruction Fetch steget library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_signed.all; entity IF_stage is port( branch_taken : in STD_LOGIC; clk : in STD_LOGIC; reset : in STD_LOGIC; clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; safe,safe2 : in STD_LOGIC; NEXT_PC : in STD_LOGIC_VECTOR (12 downto 0 retry,retry2 : in STD_LOGIC; ROM_data : in STD_LOGIC_VECTOR (63 downto 0 trap_busy : in std_logic; HW_TRAP : in std_logic; ex_trap : in std_logic; failure_bus : out std_logic_vector(13 downto 0 NOP : out STD_LOGIC_VECTOR (4 downto 0 OP : out STD_LOGIC_VECTOR (4 downto 0 PC : out STD_LOGIC_VECTOR (12 downto 0 wb_tag : out STD_LOGIC_VECTOR (1 downto 0 imm_ximm_tag : out STD_LOGIC_VECTOR (3 downto 0 ROM_ADDR : buffer STD_LOGIC_VECTOR (15 downto 0 addr2 : out STD_LOGIC_VECTOR (4 downto 0 addr_mode : out STD_LOGIC_VECTOR (1 downto 0 berger_code : out STD_LOGIC_VECTOR (4 downto 0 hw_trap_out : out STD_LOGIC; trap_retry : out std_logic; dest : out STD_LOGIC_VECTOR (4 downto 0 src1 : out STD_LOGIC_VECTOR (4 downto 0 src2 : out STD_LOGIC_VECTOR (11 downto 0 74
75 pulse_out end IF_stage; : out STD_LOGIC architecture IF_arch of IF_stage is signal PC_OUT : STD_LOGIC_VECTOR (12 downto 0 signal XADDR_MODE : STD_LOGIC_VECTOR (1 downto 0 signal XDEST : STD_LOGIC_VECTOR (4 downto 0 signal XNOP : STD_LOGIC_VECTOR (4 downto 0 signal XOP : STD_LOGIC_VECTOR (4 downto 0 signal XPC : STD_LOGIC_VECTOR (12 downto 0 signal XSRC2 : STD_LOGIC_VECTOR (11 downto 0 signal BUS1579 : STD_LOGIC_VECTOR (4 downto 0 signal BUS1581 : STD_LOGIC_VECTOR (1 downto 0 signal BUS1583 : STD_LOGIC_VECTOR (4 downto 0 signal o_im_failure :STD_LOGIC; signal o_instr_failure, trap: STD_LOGIC; signal o_nop : STD_LOGIC_VECTOR (4 downto 0 signal o_op : STD_LOGIC_VECTOR (4 downto 0 signal o_pc : STD_LOGIC_VECTOR (12 downto 0 signal o_rom_addr : STD_LOGIC_VECTOR (15 downto 0 signal o_addr2 : STD_LOGIC_VECTOR (4 downto 0 signal o_addr_mode :STD_LOGIC_VECTOR (1 downto 0 signal o_berger_code : STD_LOGIC_VECTOR (4 downto 0 signal o_dest : STD_LOGIC_VECTOR (4 downto 0 signal o_src1 : STD_LOGIC_VECTOR (4 downto 0 signal o_src2 : STD_LOGIC_VECTOR (11 downto 0 signal o_wb_tag : STD_LOGIC_VECTOR(1 downto 0 signal o_imm_ximm_tag : STD_LOGIC_VECTOR(3 downto 0 signal pulse : std_logic; signal t_retry : std_logic; component IM port ( pulse : out std_logic; trap_busy: in std_logic; PC : in STD_LOGIC_VECTOR (12 downto 0 ROM_data : in STD_LOGIC_VECTOR (63 downto 0 branch_taken : in STD_LOGIC; retry : in STD_LOGIC; clk : in STD_LOGIC; reset : in STD_LOGIC; ROM_ADDR : buffer STD_LOGIC_VECTOR (15 downto 0 addr_mode : out STD_LOGIC_VECTOR (1 downto 0 berger_code : out STD_LOGIC_VECTOR (4 downto 0 dest : out STD_LOGIC_VECTOR (4 downto 0 addr2 : out STD_LOGIC_VECTOR (4 downto 0 imm_ximm_tag : out STD_LOGIC_VECTOR (3 downto 0 wb_tag : out STD_LOGIC_VECTOR (1 downto 0 im_failure, trap_out : out STD_LOGIC; instr_failure : out STD_LOGIC; src1 : out STD_LOGIC_VECTOR (4 downto 0 src2 : out STD_LOGIC_VECTOR (11 downto 0 NOP : buffer STD_LOGIC_VECTOR (4 downto 0 OP : buffer STD_LOGIC_VECTOR (4 downto 0 HW_TRAP : in STD_LOGIC; ex_trap : in STD_LOGIC end component ; component PC_COUNTER port ( safe, safe2, trap : in STD_LOGIC; pc : in STD_LOGIC_VECTOR (12 downto 0 pc_out : out STD_LOGIC_VECTOR (12 downto 0) end component ; 75
76 component PC_MUX port ( NEXT_PC : in STD_LOGIC_VECTOR (12 downto 0 branch_pc : in STD_LOGIC_VECTOR (12 downto 0 branch_taken : in STD_LOGIC; clk : in STD_LOGIC; reset : in STD_LOGIC; retry : in STD_LOGIC; retry2 : in STD_LOGIC; trap_retry : out std_logic; PC_out : out STD_LOGIC_VECTOR (12 downto 0) end component ; U0 : PC_MUX port map( NEXT_PC => pc_out, PC_out => XPC, branch_pc => NEXT_PC, branch_taken => branch_taken, clk => clk, reset => reset, trap_retry => t_retry, retry => retry, retry2 => retry2 U1 : IM port map( ins_nop => insert_nop, pulse => pulse, trap_busy => trap_busy, trap_out => trap, NOP => XNOP, OP => XOP, PC => XPC, imm_ximm_tag=>o_imm_ximm_tag, wb_tag=>o_wb_tag, retry => retry, ROM_ADDR => o_rom_addr, ROM_data => ROM_data, addr_mode => xaddr_mode, addr2 => o_addr2, berger_code => o_berger_code, branch_taken => branch_taken, clk => clk, dest => xdest, im_failure => o_im_failure, instr_failure => o_instr_failure, reset => reset, src1 => o_src1, src2 => xsrc2, HW_trap =>HW_TRAP, ex_trap => ex_trap U4 : PC_COUNTER port map( trap => trap, safe => safe, safe2 => safe2, pc => XPC, pc_out => pc_out O_ADDR_MODE <= xaddr_mode; O_DEST <= xdest; 76
77 NOP <= XNOP; O_OP <= XOP; O_PC <= pc_out; O_SRC2 <= xsrc2; ROM_addr <= o_rom_addr; failure_bus(1) <= o_instr_failure; pipe_reg:process(clk, reset, clear_reg, clear_reg2) is if reset = '1' or clear_reg = '1' or clear_reg2 = '1' then OP <=(others => '0' PC <= (others => '0' src1 <= (others => '0' src2 <=(others => '0' dest <= (others => '0' berger_code <=(others => '0' addr_mode <= (others => '0' addr2 <= (others => '0' failure_bus(0) <= '0'; failure_bus(13 downto 2) <= (others => '0' hw_trap_out <= '0'; trap_retry <= '0'; pulse_out <='0'; wb_tag <=(others => '1' imm_ximm_tag <= (others => '0' elsif clk'event and clk = '1' then hw_trap_out <= trap; OP <= o_op; PC <= o_pc; src1 <= o_src1; src2 <= o_src2; dest <= o_dest; failure_bus(0)<= o_im_failure; failure_bus(13 downto 2) <= (others => '1' berger_code <= o_berger_code; addr_mode <= o_addr_mode; addr2 <= o_addr2; Output = o_addr2_!!!! trap_retry <= t_retry; pulse_out <= pulse; wb_tag <= o_wb_tag; imm_ximm_tag <= o_imm_ximm_tag; end process pipe_reg; end IF_arch; Title : IM Design : xjobb Author : Andreas Söderberg Company : SP File : IM.vhd Version : 1.0 Date : Rev. by. : Description : Hanterar upplasning av instruktioner library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_unsigned.all; use IEEE.std_logic_arith.all; entity IM is 77
78 port ( clk : in STD_LOGIC; reset : in STD_LOGIC; trap_busy : in STD_LOGIC; HW_TRAP : in STD_LOGIC; retry : in STD_LOGIC; branch_taken : in STD_LOGIC; ex_trap : in std_logic; ROM_data : in STD_LOGIC_VECTOR (63 downto 0 PC : in STD_LOGIC_VECTOR (12 downto 0 im_failure : out STD_LOGIC; instr_failure : out STD_LOGIC; trap_out : out STD_LOGIC; pulse : out STD_LOGIC; berger_code : out STD_LOGIC_VECTOR (4 downto 0 dest : out STD_LOGIC_VECTOR (4 downto 0 src1 : out STD_LOGIC_VECTOR (4 downto 0 src2 : out STD_LOGIC_VECTOR (11 downto 0 addr2 : out STD_LOGIC_VECTOR (4 downto 0 addr_mode : out STD_LOGIC_VECTOR (1 downto 0 imm_ximm_tag : out STD_LOGIC_VECTOR (3 downto 0 wb_tag : out STD_LOGIC_VECTOR (1 downto 0 ROM_ADDR : buffer STD_LOGIC_VECTOR (15 downto 0 OP : buffer STD_LOGIC_VECTOR (4 downto 0 NOP : buffer STD_LOGIC_VECTOR (4 downto 0) end IM; architecture IM of IM is signal mem_counter : INTEGER range 0 to 7; signal f_counter : integer; signal berger_check, berger_im : std_logic_vector(5 downto 0 signal CRC_temp : std_logic_vector(3 downto 0 signal next_op, NOP_temp : std_logic_vector(4 downto 0 signal PCS1, next_pcs1 : STD_LOGIC_VECTOR (3 downto 0 signal PCS2, next_pcs2 : STD_LOGIC_VECTOR (3 downto 0 signal branch : STD_LOGIC; signal counter : integer range 0 to 6; type PCS_T is array (6 downto 0) of STD_LOGIC_VECTOR(3 downto 0 signal PCS_stack : PCS_T; type NEXTOP_T is array (6 downto 0) of STD_LOGIC_VECTOR(4 downto 0 signal NEXTOP_stack : NEXTOP_T; signal retr_flag : std_logic; signal trap, busy : std_logic; signal ins_nop,rft : std_logic; signal PCS_trap : std_logic_vector(3 downto 0 signal NOP_trap : std_logic_vector(4 downto 0 signal rft_fin : std_logic; function count(a: std_logic_vector(2 downto 0)) return std_logic_vector is variable sum : std_logic_vector(1 downto 0 case (a) is when "000" => sum:="11"; when "001" => sum:="10"; when "010" => sum:="10"; when "011" => sum:="01"; when "100" => sum:="10"; when "101" => sum:="01"; when "110" => sum:="01"; when "111" => sum:="00"; when others => null; end case; return sum; end count; 78
79 process(clk, reset) is Pipe counter if reset = '1' then counter <= 1; f_counter<=0; elsif clk'event and clk='1' then if counter < 6 then counter <= counter + 1; else counter <= 0; f_counter<=f_counter+1; pulse <= conv_std_logic_vector(counter,3)(0 end process; process(clk, reset) is if reset = '1' then rft_fin <= '0'; rft<='0'; ins_nop<='0'; next_op <= "01100"; next_pcs1 <="0000"; next_pcs2 <="0000"; branch <='0'; for i in 0 to 6 loop NEXTOP_stack(i)<="01100"; PCS_stack(i) <= "0000"; end loop; NOP <="01100"; trap <= '0'; trap_out <= '0'; busy <= '0'; NOP_trap <= (others => '0' PCS_trap <= (others => '0' elsif (clk'event and clk='1') then if busy='0' and (HW_TRAP='1' or ex_trap = '1') and OP/="01101" and OP/="01100" and branch_taken='0' then trap <='1'; trap_out <='1'; busy<='1'; else trap<='0'; trap_out<='0'; ins_nop<=trap; if retry='0' then NEXTOP_stack(counter)<= NOP_temp; next_pcs1 <= PCS1; next_pcs2 <= PCS2; next_op <= NOP_temp; NOP <= NOP_temp; else next_pcs1 <= PCS_stack(counter next_pcs2 <= PCS_stack(counter next_op <= NEXTOP_stack(counter NOP <= NEXTOP_stack(counter trap_out<='0'; if OP="01111" then NOP_trap <= NOP_temp; PCS_trap <= PCS1; if OP = "01110" then rft<='1'; rft_fin <= '1'; else 79
80 rft<='0'; if rft='1' then busy<='0'; NOP <= NOP_trap; next_op <= NOP_trap; next_pcs2 <= PCS_trap; if HW_TRAP='0' and rft_fin = '1' then busy <= '0'; rft_fin <= '0'; if branch_taken='0' then PCS_stack(counter)<= PCS1; else PCS_stack(counter)<= PCS2; branch <= branch_taken; end process; ROM_addr <= "000"&PC; process(rom_data, ROM_addr) variable temp_data : std_logic_vector (7 downto 0 variable temp_addr : std_logic_vector (2 downto 0 variable temp_berger : std_logic_vector (5 downto 0 type crc is array (5 downto 0) of STD_LOGIC_VECTOR(3 downto 0 variable temp_crc : crc; temp_berger :="000000"; temp_crc(0):="0000"; for i in 0 to 15 loop temp_berger :=count(rom_data(((i+6)*3) downto ((i+5)*3)+1))+temp_berger; end loop; berger_check <= temp_berger; for i in 0 to 4 loop temp_addr := ROM_addr(((i+1)*3-1) downto i*3 temp_crc(i+1)(0) := temp_addr(2) xor temp_addr(1) xor temp_addr(0) xor temp_crc(i)(1) xor temp_crc(i)(2) xor temp_crc(i)(3 temp_crc(i+1)(1) := temp_addr(0) xor temp_crc(i)(1 temp_crc(i+1)(2) := temp_addr(1) xor temp_crc(i)(2 temp_crc(i+1)(3) := temp_addr(1) xor temp_addr(0) xor temp_crc(i)(0) xor temp_crc(i)(1) xor temp_crc(i)(2 end loop; CRC_temp<= temp_crc(5 end process; process(rom_data, trap, trap_busy, ins_nop, next_pcs1) is variable mux_mode : std_logic_vector (1 downto 0 variable mux_src2 : std_logic_vector (4 downto 0 variable mux_dest : std_logic_vector (4 downto 0 addr_mode <= ROM_data(63 downto 62 mux_mode := ROM_data(63 downto 62 OP <= ROM_data(61 downto 57 NOP_temp <= ROM_data(56 downto 52 PCS1 <= ROM_data(51 downto 48 PCS2 <= ROM_data(47 downto 44 dest <= ROM_data(43 downto 39 mux_dest := ROM_data(43 downto 39 src1 <= ROM_data(38 downto 34 src2 <= ROM_data(33 downto 22 mux_src2 := ROM_data(26 downto 22 berger_code <= ROM_data(21 downto 17 80
81 berger_im <= ROM_data(15 downto 10 imm_ximm_tag <= ROM_data(9 downto 6 wb_tag <= ROM_data(5 downto 4 if trap='1' and trap_busy='0' then ADDR_MODE<="01"; OP<="01111"; NOP_temp<="00000"; PCS1<=next_PCS1; dest<="11111"; src1<="00000"; src2<=" "; berger_code<="10111"; if ins_nop = '1' then ADDR_MODE<="00"; mux_mode:="01"; OP <="00000"; NOP_temp<="00000"; PCS1<="0000"; PCS2<="1011"; dest<="00000"; mux_dest:="00000"; src1<="00000"; src2<=" "; mux_src2:="00000"; berger_code<="00000"; if mux_mode = "00" then addr2 <= mux_src2; else addr2 <= mux_dest; end process; process(berger_check, berger_im) if berger_im=berger_check then im_failure<='0'; else im_failure<='1'; end process; process(next_pcs1, next_pcs2, CRC_temp, OP, next_op, branch, retry, reset) is if retry = '1' then retr_flag <= '1'; elsif reset = '1' then retr_flag <= '0'; instr_failure <= '0'; if next_op /= OP and OP/="01111" then instr_failure <= '1'; if branch='0' and CRC_temp /= next_pcs1 then instr_failure <= '1'; elsif branch='1' and CRC_temp /= next_pcs2 then instr_failure <= '1'; end process; end IM; 81
82 Title : PC-counter Design : xjobb Author : Andreas Söderberg Company : SP File : pc_conter.vhd Version : 1.0 Date : Rev. by. : Description : Räknare för instruktionsminnet library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_unsigned.all; entity PC_counter is port ( safe, safe2, trap : in STD_LOGIC; pc : in STD_LOGIC_VECTOR (12 downto 0 pc_out : out STD_LOGIC_VECTOR (12 downto 0) end PC_counter; architecture PC_counter_arch of PC_counter is process(pc, safe, safe2, trap) variable add : std_logic; add:=(not trap) and (not safe) and (not safe2 pc_out<=pc+add; end process; end PC_counter_arch; Title : PC_mux Design : xjobb Author : Andreas Söderberg Company : SP File : pc_mux.vhd Version : 1.0 Date : Rev. by. : 82
83 Description : Väljer programräknare beroende på hopp och retry library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_unsigned.all; entity PC_MUX is port ( NEXT_PC: in STD_LOGIC_VECTOR (12 downto 0 branch_pc: in STD_LOGIC_VECTOR (12 downto 0 branch_taken: in STD_LOGIC; retry: in STD_LOGIC; retry2: in STD_LOGIC; reset: in STD_LOGIC; clk : in STD_LOGIC; trap_retry: out std_logic; PC_out: out STD_LOGIC_VECTOR (12 downto 0) end PC_MUX; architecture PC_MUX of PC_MUX is type T_STACK is array (6 downto 0) of STD_LOGIC_VECTOR(12 downto 0 type T_int is array (0 to 6) of integer range 0 to 6; signal counter : integer range 0 to 6; signal STACK: T_STACK; signal PC: STD_LOGIC_VECTOR (12 downto 0 process(clk, reset) is Pipe counter if reset = '1' then counter <= 1; elsif clk'event and clk='1' then if counter < 6 then counter <= counter + 1; else counter <= 0; end process; STACK_PC:process(NEXT_PC, branch_taken, branch_pc, retry, retry2, counter) if retry = '1' or retry2='1' then Stack PC PC <= STACK(counter elsif branch_taken='0' then PC <= NEXT_PC; else PC <= branch_pc; end process STACK_PC; process(clk, reset) if reset='1' then PC_out <=(others =>'0' for i in 0 to 6 loop STACK(i)<= (others =>'0' end loop; trap_retry <= '0'; elsif clk'event and clk='1' then PC_out<=pc; STACK(counter)<= PC; 83
84 end PC_MUX; trap_retry <= retry; end process; Title : ID-steget Design : xjobb Author : Andreas Soderberg Company : SP File : id.vhd Version : 1.0 Date : Rev. by. : Description : Sammankoppling av blocken i ID-steget library IEEE; use IEEE.std_logic_1164.all; entity READ_REG is port( CLK : in STD_LOGIC; trap_retry : in std_logic; RESET : in STD_LOGIC; clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; i_check : in STD_LOGIC; in_pulse : in STD_LOGIC; reg_disable : in STD_LOGIC; addr2 : in STD_LOGIC_VECTOR (4 downto 0 imm_xim_tag : in STD_LOGIC_VECTOR (3 downto 0 wb_tag : in STD_LOGIC_VECTOR (1 downto 0 PC : in STD_LOGIC_VECTOR (12 downto 0 failure_bus_in : in std_logic_vector(13 downto 0 addr_mode : in STD_LOGIC_VECTOR (1 downto 0 alu_addr : in STD_LOGIC_VECTOR (5 downto 0 alu_data : in STD_LOGIC_VECTOR (31 downto 0 alu_addr2 : in STD_LOGIC_VECTOR (5 downto 0 alu_data2 : in STD_LOGIC_VECTOR (31 downto 0 berger_code : in STD_LOGIC_VECTOR (4 downto 0 dest : in STD_LOGIC_VECTOR (4 downto 0 write_addr : in STD_LOGIC_VECTOR (4 downto 0 write_data : in STD_LOGIC_VECTOR (31 downto 0 bp_addr : in STD_LOGIC_VECTOR (5 downto 0 bp_data : in STD_LOGIC_VECTOR (31 downto 0 nopcode : in STD_LOGIC_VECTOR (4 downto 0 opcode : in STD_LOGIC_VECTOR (4 downto 0 src1 : in STD_LOGIC_VECTOR (4 downto 0 84
85 end READ_REG; src2 : in STD_LOGIC_VECTOR (11 downto 0 TSTout : out STD_LOGIC; branch_taken : out STD_LOGIC; trap_out : out STD_LOGIC; out_pulse : out STD_LOGIC; O_wb_tag : out STD_LOGIC_VECTOR (1 downto 0 failure_bus : out STD_LOGIC_VECTOR (13 downto 0 o_ddest : out STD_LOGIC_VECTOR (28 downto 0 o_next_pc : out STD_LOGIC_VECTOR (12 downto 0 o_rdest : out STD_LOGIC_VECTOR (5 downto 0 o_data1 : out STD_LOGIC_VECTOR (28 downto 0 o_data2 : out STD_LOGIC_VECTOR (28 downto 0 o_nopcode : out STD_LOGIC_VECTOR (4 downto 0 o_opcode : out STD_LOGIC_VECTOR (4 downto 0) architecture READ_REG of READ_REG is signal OADDR2 : STD_LOGIC_VECTOR (4 downto 0 signal OOPCODE : STD_LOGIC_VECTOR (4 downto 0 signal ORDEST : STD_LOGIC_VECTOR (4 downto 0 signal XNOPCODE : STD_LOGIC_VECTOR (4 downto 0 signal BUS2607 : STD_LOGIC_VECTOR (4 downto 0 signal dest_out : STD_LOGIC_VECTOR (5 downto 0 signal OCTRL : STD_LOGIC_VECTOR (7 downto 0 signal BUS1378 : STD_LOGIC_VECTOR (28 downto 0 signal BUS2552 : STD_LOGIC_VECTOR (28 downto 0 signal BUS2556 : STD_LOGIC_VECTOR (28 downto 0 signal BUS988 : STD_LOGIC_VECTOR (28 downto 0 signal XDATA1 : STD_LOGIC_VECTOR (28 downto 0 signal out_data2 : STD_LOGIC_VECTOR (28 downto 0 signal ODDEST : STD_LOGIC_VECTOR (29 downto 0 signal XDATA2 : STD_LOGIC_VECTOR (31 downto 0 signal NET1285 : STD_LOGIC; signal o_addr_failure : STD_LOGIC; signal o_branch_failure : STD_LOGIC; signal o_decode_failure : STD_LOGIC; signal o_branch_taken : STD_LOGIC; signal trap_net : STD_LOGIC; signal o_rbank_failure : STD_LOGIC; signal o_forw_failure : STD_LOGIC; signal o_imm_ximm_failure : STD_lOGIC; signal i_reg_tst_flg : STD_LOGIC; signal i_clr_trap_busy : std_logic; component SRC2_MUX port ( imm_ximm_tag : in STD_LOGIC_VECTOR(3 downto 0 RFT : in std_logic; addr_mode : in STD_LOGIC_VECTOR(1 downto 0 DDEST : in STD_LOGIC_VECTOR (29 downto 0 branch, trap : in STD_LOGIC; data2 : in STD_LOGIC_VECTOR (31 downto 0 odata2 : out STD_LOGIC_VECTOR (28 downto 0 imm_ximm_failure : out STD_LOGIC end component; component BRANCH port ( trap_retry: in std_logic; DDEST : in STD_LOGIC_VECTOR (29 downto 0 PC : in STD_LOGIC_VECTOR (12 downto 0 TRAP : in STD_LOGIC; branch_ctrl : in STD_LOGIC_VECTOR (1 downto 0 branch_select : in STD_LOGIC; data1 : in STD_LOGIC_VECTOR (28 downto 0 data2 : in STD_LOGIC_VECTOR (31 downto 0 85
86 NEXT_PC : out STD_LOGIC_VECTOR (12 downto 0 clr_trap_busy : out std_logic; branch_failure : out STD_LOGIC; branch_taken : out STD_LOGIC; trap_busy : in STD_LOGIC end component; component DECODE port ( RST : in STD_LOGIC; clk : in STD_LOGIC; clr_trap_busy : in std_logic; trap_busy : out std_logic; opcode : in STD_LOGIC_VECTOR (4 downto 0 ctrl : out STD_LOGIC_VECTOR (7 downto 0 decode_failure : out STD_LOGIC end component ; component FORWARD port ( alu_addr : in STD_LOGIC_VECTOR (5 downto 0 alu_data : in STD_LOGIC_VECTOR (31 downto 0 alu_addr2 : in STD_LOGIC_VECTOR (5 downto 0 alu_data2 : in STD_LOGIC_VECTOR (31 downto 0 dest_addr : in STD_LOGIC_VECTOR (4 downto 0 dest_data : in STD_LOGIC_VECTOR (31 downto 0 bp_addr : in STD_LOGIC_VECTOR (5 downto 0 bp_data : in STD_LOGIC_VECTOR (31 downto 0 TST : in STD_LOGIC; src1_addr : in STD_LOGIC_VECTOR (4 downto 0 src2_addr : in STD_LOGIC_VECTOR (4 downto 0 src_one : in STD_LOGIC_VECTOR (28 downto 0 src_two : in STD_LOGIC_VECTOR (28 downto 0 forw_failure : out STD_LOGIC; src_one_out : out STD_LOGIC_VECTOR (28 downto 0 src_two_out : out STD_LOGIC_VECTOR (28 downto 0) end component ; component IMM_XIM port ( PC : in STD_LOGIC_VECTOR (12 downto 0 RFT : in STD_LOGIC; TRAP : in STD_LOGIC; TST : in STD_LOGIC; addr_mode : in STD_LOGIC_VECTOR (1 downto 0 berger_code : in STD_LOGIC_VECTOR (4 downto 0 dest : in STD_LOGIC_VECTOR (4 downto 0 reg_data_2 : in STD_LOGIC_VECTOR (28 downto 0 src2 : in STD_LOGIC_VECTOR (11 downto 0 DDEST : out STD_LOGIC_VECTOR (29 downto 0 addr_failure : out STD_LOGIC; reg_tst_flg : out STD_LOGIC; data2 : out STD_LOGIC_VECTOR (31 downto 0) end component ; component MUX_SRC1 port ( IN_RDEST : in STD_LOGIC_VECTOR (4 downto 0 forward_ok : in STD_LOGIC; RDEST : out STD_LOGIC_VECTOR (5 downto 0) end component ; component REG_FILE 86
87 port ( addr1 : in STD_LOGIC_VECTOR (4 downto 0 addr2 : in STD_LOGIC_VECTOR (4 downto 0 check : in STD_LOGIC; clk : in STD_LOGIC; extra_check : in STD_LOGIC; write_addr : in STD_LOGIC_VECTOR (4 downto 0 write_data : in STD_LOGIC_VECTOR (31 downto 0 rbank_failure : out STD_LOGIC; data1 : out STD_LOGIC_VECTOR (28 downto 0 data2 : out STD_LOGIC_VECTOR (28 downto 0) end component ; U6 : SRC2_MUX port map( imm_ximm_tag => imm_xim_tag, addr_mode => addr_mode, RFT => OCTRL(2), trap => OCTRL(1), DDEST => ODDEST, branch => OCTRL(0), data2 => XDATA2, odata2 => out_data2, imm_ximm_failure => o_imm_ximm_failure U0 : IMM_XIM port map( DDEST => ODDEST, PC => PC, reg_tst_flg => i_reg_tst_flg, RFT => OCTRL(2), TST => OCTRL(7), TRAP => OCTRL(1), addr_failure => o_addr_failure, addr_mode => addr_mode, berger_code => berger_code, data2 => XDATA2, dest => ORDEST, reg_data_2 => BUS988, src2 => src2 U1 : REG_FILE port map( addr1 => src1, addr2 => OADDR2, check => i_check, clk => CLK, data1 => BUS2552, data2 => BUS2556, extra_check => reg_disable, rbank_failure => o_rbank_failure, write_addr => write_addr, write_data => write_data U3 : BRANCH port map( trap_retry => trap_retry, clr_trap_busy =>i_clr_trap_busy, branch_ctrl(0) => OOPCODE(0), branch_ctrl(1) => OOPCODE(1), DDEST => ODDEST, NEXT_PC => o_next_pc, PC => PC, 87
88 U2 : DECODE port map( TRAP => OCTRL(1), branch_failure => o_branch_failure, branch_select => OCTRL(0), branch_taken => o_branch_taken, data1 => XDATA1, data2 => XDATA2, trap_busy => trap_net clr_trap_busy => i_clr_trap_busy, RST => RESET, clk => clk, trap_busy => trap_net, ctrl => OCTRL, decode_failure => o_decode_failure, opcode => OOPCODE U4 : MUX_SRC1 port map( IN_RDEST => ORDEST, RDEST => dest_out, forward_ok => OCTRL(5) U5 : FORWARD port map( alu_addr => alu_addr, alu_data => alu_data, alu_addr2 => alu_addr2, alu_data2 => alu_data2, TST => OCTRL(7), dest_addr => write_addr, dest_data => write_data, bp_addr => bp_addr, bp_data => bp_data, src1_addr => src1, src2_addr => OADDR2, src_one => BUS2552, src_one_out => BUS1378, forw_failure => o_forw_failure, src_two => BUS2556, src_two_out => BUS988 xdata1 <= BUS1378; ORDEST <= DEST; XNOPCODE <= NOPCODE; OOPCODE <= OPCODE; OADDR2 <= ADDR2; branch_taken <= o_branch_taken; failure_bus(1) <= failure_bus_in(1 TSTout <= OCTRL(7 trap_out <= trap_net; process(reset, clk, clear_reg, clear_reg2) is if reset = '1' or clear_reg = '1' or clear_reg2 = '1' then O_DATA1 <= "11"&(26 downto 0 => '0' O_DATA2 <= "11"&(26 downto 0 => '0' O_DDEST <= "11"&(26 downto 0 => '0' O_NOPCODE <=(others => '0' O_OPCODE <=(others => '0' O_RDEST <=(others => '0' O_wb_tag <=(others => '1' failure_bus(0) <= '0'; 88
89 failure_bus(13 downto 2) <= (13 downto 2 => '0' out_pulse <= '1'; elsif clk'event and clk='1' then O_DATA1 <= XDATA1; O_DATA2 <= out_data2; O_DDEST <= ODDEST(28 downto 0 O_NOPCODE <= XNOPCODE; O_OPCODE <= OOPCODE; O_RDEST <= dest_out; O_wb_tag <= wb_tag; failure_bus(0) <= failure_bus_in(0 failure_bus(2) <= o_addr_failure and failure_bus_in(2 failure_bus(3)<= o_branch_failure and failure_bus_in(3 failure_bus(4) <= o_decode_failure and failure_bus_in(4 failure_bus(5) <= o_branch_taken and failure_bus_in(5 failure_bus(9 downto 6) <= failure_bus_in(9 downto 6 failure_bus(10) <= o_imm_ximm_failure and failure_bus_in(10 failure_bus(11) <= o_forw_failure and failure_bus_in(11 failure_bus(12) <= ((o_rbank_failure and not OCTRL(6))and not i_reg_tst_flg) and failure_bus_in(12 failure_bus(13) <= failure_bus_in(13 out_pulse <= in_pulse; end process; end READ_REG; Title : SRC2-mux Design : xjobb Author : Andreas Soderberg Company : SP File : src2_mux.vhd Version : 1.0 Date : Rev. by. : Description : Multiplexer fr SRC2 med "tag"-test library IEEE; use IEEE.std_logic_1164.all; entity src2_mux is port ( branch, trap, RFT : in STD_LOGIC; DDEST : in STD_LOGIC_VECTOR (29 downto 0 data2 : in STD_LOGIC_VECTOR (31 downto 0 imm_ximm_tag : in STD_LOGIC_VECTOR (3 downto 0 addr_mode : in STD_LOGIC_VECTOR (1 downto 0 imm_ximm_failure : out STD_LOGIC; end src2_mux; odata2 : out STD_LOGIC_VECTOR (28 downto 0) architecture src2_mux of src2_mux is signal data2_t : STD_LOGIC_VECTOR(31 downto 0 process(branch, DDEST, data2, trap, RFT) if branch = '1' and trap='0' and RFT ='0' then data2_t <= '1'&data2(30 downto 29)&DDEST(28 downto 0 89
90 else data2_t <= '0'&data2(30 downto 0 end process; process (branch, DDEST, TRAP, RFT, addr_mode, data2_t,imm_ximm_tag) variable mux1_tag : STD_LOGIC_VECTOR(2 downto 0 variable mux2_tag : STD_LOGIC; case addr_mode is when "00" => Set tags mux1_tag := "000"; mux2_tag := '0'; when "01" => mux1_tag := "001"; if TRAP = '1' then mux2_tag := '1'; else mux2_tag := '0'; end process; end src2_mux; when "10" => mux1_tag := "010"; mux2_tag := '0'; when others => mux1_tag := "111"; mux2_tag := '1'; end case; if branch = '1' and trap='0' and RFT ='0' then mux1_tag(2) := '1'; Comparator 1 if data2_t(31 downto 29)/=mux1_tag or DDEST(29) /= mux2_tag then imm_ximm_failure <= '1'; else imm_ximm_failure <= '0'; Comparator 2 if data2_t(31 downto 29)/=imm_ximm_tag(2 downto 0) or DDEST(29) /= imm_ximm_tag(3) then odata2 <= "11111"&(23 downto 0 => '0' else odata2 <= data2_t(28 downto 0 Title : Branch-blocket Design : xjobb Author : Andreas Soderberg Company : SP File : branch.vhd Version : 1.0 Date : Rev. by. : Description : Hanterar villkorliga och ovillkorliga hopp 90
91 library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_signed.all; entity BRANCH is port ( trap_retry : in std_logic; clr_trap_busy : out std_logic; PC : in STD_LOGIC_VECTOR (12 downto 0 data2 : in STD_LOGIC_VECTOR (31 downto 0 data1 : in STD_LOGIC_VECTOR (28 downto 0 DDEST : in STD_LOGIC_VECTOR (29 downto 0 branch_ctrl : in STD_LOGIC_VECTOR (1 downto 0 branch_select : in STD_LOGIC; TRAP : in STD_LOGIC; trap_busy : in STD_LOGIC; branch_taken : out STD_LOGIC; NEXT_PC : out STD_LOGIC_VECTOR (12 downto 0 branch_failure : out STD_LOGIC end BRANCH; architecture BEH_BRANCH of BRANCH is signal trap_busy_int : std_logic; process (branch_select, branch_ctrl, DDEST, data1, data2,pc, trap, trap_retry) variable branch : STD_LOGIC_VECTOR (3 downto 0 variable fault : STD_LOGIC; branch (1 downto 0) := branch_ctrl; branch (2) := branch_select; branch(3) := TRAP; case branch is when "0100" => BEQ clr_trap_busy <= '0'; if data1 = DDEST(28 downto 0) then NEXT_PC <= PC + data2(12 downto 0 branch_taken <= '1'; fault := '0'; else branch_taken <= '0'; NEXT_PC <= PC; fault := '0'; when "0101" => BNE clr_trap_busy <= '0'; if data1 /= DDEST(28 downto 0) then NEXT_PC <= PC + data2(12 downto 0 branch_taken <= '1'; fault := '0'; else branch_taken <= '0'; NEXT_PC <= PC; fault := '0'; when "0110" => RFT (jmp) NEXT_PC <= DDEST(12 downto 0 in the IF-stage and in reg R31 branch_taken <= '1'; fault := '0'; clr_trap_busy <= '1'; pre-stored 91
92 when "0111" => RESET clr_trap_busy <= '0'; NEXT_PC <= (others => '0' branch_taken <= '1'; fault := '0'; when "1111" => TRAP clr_trap_busy <= '0'; if ((trap_busy = '0') and (data2(28 downto 0) = " ")) or (trap_retry = '1') then branch_taken <= '1'; NEXT_PC <= data2(12 downto 0 fault := '0'; else fault := '1'; NEXT_PC <= PC; branch_taken <= '0'; when "1000" => TST clr_trap_busy <= '0'; fault := '1'; NEXT_PC <= PC; branch_taken <= '0'; when others => clr_trap_busy <= '0'; branch_taken <= '0'; NEXT_PC <= PC; fault := '0'; end case; all signals if fault <= '0' then branch_failure <= '0'; else branch_failure <= '1'; Flag the failure and clear end process; end BEH_BRANCH; Title : Decode-blocket Design : xjobb Author : Andreas Soderberg Company : SP File : decode.vhd Version : 1.0 Date : Rev. by. : Description : Ger styrsignaler till ovriga processorn ctrl: b0 => branch flag b1 => trap flag b2 => RFT flag b3 => Available bit b4 => Available bit 92
93 b5 => Does not forward b6 => Disable reg_file test flag b7 => Test instruction flag Sets flag: TRAP_BUSY library IEEE; use IEEE.std_logic_1164.all; entity DECODE is port ( RST,clk : in std_logic; clr_trap_busy : in std_logic; opcode : in STD_LOGIC_VECTOR (4 downto 0 ctrl : out STD_LOGIC_VECTOR (7 downto 0 decode_failure : out STD_LOGIC; trap_busy : out STD_LOGIC end DECODE; architecture DECODE_beh of DECODE is signal trap_busy_temp : STD_LOGIC; process(opcode, RST, clr_trap_busy) is variable fault: STD_LOGIC; fault := '0'; case opcode is when "00000" => ctrl <= " "; ADD when "00001" => ctrl <= " "; SUB when "00010" => ctrl <= " "; ANDA when "00011" => ctrl <= " "; ORA when "00100" => ctrl <= " "; XORA when "00101" => ctrl <= " "; CMP when "00110" => ctrl <= " "; ADDV when "00111" => ctrl <= " "; SUBV when "01000" => ctrl <= " "; LLS when "01001" => ctrl <= " "; LRS when "01010" => ctrl <= " "; ALS when "01011" => ctrl <= " "; ARS h00 h01 h02 h03 h04 h05 h06 h07 h08 h09 ha hb when "01100" => ctrl <= " "; BEQ hc when "01101" => ctrl <= " "; BNE hd when "01110" => ctrl <= " "; RFT (JMP) he when "01111" => ctrl <= " "; TRAP hf trap_busy_temp <= '1'; when "10000" => ctrl <= " "; READ h10 when "10001" => ctrl <= " "; LW h11 when "10010" => ctrl <= " "; PUT h12 when "10011" => ctrl <= " "; SW h13 when "10110" => ctrl <= " "; PRT h16 when "10111" => ctrl <= " "; SFE h17 fault := '1'; when "11000" => ctrl <= " "; TST h18 fault := '1'; when "11111" => ctrl <= " "; RST h1f trap_busy_temp<='0'; when others => ctrl <= " "; fault := '1'; end case; if clr_trap_busy = '1' or rst='1' then trap_busy_temp <= '0'; if fault = '0' then decode_failure <= '0'; else 93
94 decode_failure <= '1'; end process; process(clk, rst) if rst='1' then trap_busy<='0'; elsif clk'event and clk='1' then trap_busy<=trap_busy_temp; end process; end DECODE_beh; Title : Forwarding Design : xjobb Author : Tomas Holmgren Company : SP File : forward.vhd Version : 1.0 Date : Rev. by. : Andreas Soderberg Description : Hanterar forwardingen och ar skyddad av "tags" library IEEE; use IEEE.std_logic_1164.all; entity FORWARD is port ( alu_addr : in STD_LOGIC_VECTOR (5 downto 0 dest_addr : in STD_LOGIC_VECTOR (4 downto 0 bp_addr : in STD_LOGIC_VECTOR (5 downto 0 alu_addr2 : in STD_LOGIC_VECTOR (5 downto 0 alu_data2 : in STD_LOGIC_VECTOR (31 downto 0 src1_addr : in STD_LOGIC_VECTOR (4 downto 0 src2_addr : in STD_LOGIC_VECTOR (4 downto 0 alu_data : in STD_LOGIC_VECTOR (31 downto 0 dest_data : in STD_LOGIC_VECTOR (31 downto 0 bp_data : in STD_LOGIC_VECTOR (31 downto 0 TST : in STD_LOGIC; src_one : in STD_LOGIC_VECTOR (28 downto 0 src_two : in STD_LOGIC_VECTOR (28 downto 0 src_one_out : out STD_LOGIC_VECTOR (28 downto 0 src_two_out : out STD_LOGIC_VECTOR (28 downto 0 forw_failure : out STD_LOGIC end FORWARD; architecture FORWARD_arch of FORWARD is signal src_one_out_t,src_two_out_t : STD_LOGIC_VECTOR(31 downto 0 forwarding:process(src1_addr, dest_addr, dest_data, bp_addr, bp_data, alu_addr, alu_data, alu_addr2, alu_data2, src_one, src_two, src2_addr) variable src1_addr_t, src2_addr_t : STD_LOGIC_VECTOR(4 downto 0 if src1_addr="00000" then src_one_out_t<="00011"&(26 downto 0 => '0' elsif '0'&src1_addr=alu_addr then src_one_out_t<=alu_data; elsif '0'&src1_addr=alu_addr2 then 94
95 src_one_out_t<=alu_data2; elsif '0'&src1_addr=bp_addr then src_one_out_t<=bp_data; elsif src1_addr=dest_addr then src_one_out_t<=dest_data; else src_one_out_t<="101"&src_one; if src2_addr="00000" then src_two_out_t<="00011"&(26 downto 0 => '0' elsif '0'&src2_addr=alu_addr then src_two_out_t<=alu_data; elsif '0'&src2_addr=alu_addr2 then src_two_out_t<=alu_data2; elsif '0'&src2_addr=bp_addr then src_two_out_t<=bp_data; elsif src2_addr=dest_addr then src_two_out_t<=dest_data; else src_two_out_t<="101"&src_two; end process forwarding; process(tst, src_one_out_t, src_two_out_t, src1_addr, dest_addr, bp_addr, alu_addr, alu_addr2, src2_addr) variable mux1_tag, mux2_tag : STD_LOGIC_VECTOR(2 downto 0 if src1_addr="00000" then mux1_tag := "000"; elsif '0'&src1_addr=alu_addr then mux1_tag := "001"; elsif '0'&src1_addr=alu_addr2 then mux1_tag := "010"; elsif '0'&src1_addr=bp_addr then mux1_tag := "011"; elsif src1_addr=dest_addr then mux1_tag := "100"; else mux1_tag := "101"; if src2_addr="00000" then mux2_tag := "000"; elsif '0'&src2_addr=alu_addr then mux2_tag := "001"; elsif '0'&src2_addr=alu_addr2 then mux2_tag := "010"; elsif '0'&src2_addr=bp_addr then mux2_tag := "011"; elsif src2_addr=dest_addr then mux2_tag := "100"; else mux2_tag := "101"; if TST = '1' then mux1_tag := "111"; mux2_tag := "111"; if src_one_out_t(31 downto 29) /= mux1_tag or src_two_out_t(31 downto 29) /= mux2_tag then forw_failure <= '1'; else forw_failure <= '0'; end process; src_one_out <= src_one_out_t(28 downto 0 95
96 src_two_out <= src_two_out_t(28 downto 0 end FORWARD_arch; Title : IMM/XIMM-blocket Design : xjobb Author : Andreas Soderberg Company : SP File : imm_ximm.vhd Version : 1.0 Date : Rev. by. : Description : Hanterar de olika adresseringsmoderna When branch instruction: DEST, src1 addres memory => data2,data1 Immediate value in src2 => DDEST (branch vector) No limitations of reading registers due to fault persistance. library IEEE; use IEEE.std_logic_1164.all; entity IMM_XIM is port ( PC: in STD_LOGIC_VECTOR (12 downto 0 From IF dest: in STD_LOGIC_VECTOR (4 downto 0 From IF src2: in STD_LOGIC_VECTOR (11 downto 0 From IF berger_code: in STD_LOGIC_VECTOR (4 downto 0 From IF addr_mode: in STD_LOGIC_VECTOR (1 downto 0 From IF TRAP: in STD_LOGIC; From DECODE RFT: in STD_LOGIC; From DECODE TST: in STD_LOGIC; reg_data_2: in STD_LOGIC_VECTOR (28 downto 0 data2: out STD_LOGIC_VECTOR (31 downto 0 To EX DDEST : out STD_LOGIC_VECTOR (29 downto 0 To WB addr_failure: out STD_LOGIC; To fault handler reg_tst_flg: out STD_LOGIC end IMM_XIM; architecture beh_imm_xim of IMM_XIM is process (addr_mode, RFT, TRAP, src2, reg_data_2,dest,pc, berger_code, TST) is reg_data_2,dest variable fault, check_sign, sign_bit :STD_LOGIC; variable tag : STD_LOGIC_VECTOR(2 downto 0 sign_bit := src2(11 case addr_mode is when "00" => Register mode data2 <= "000"®_data_2; DDEST <= '0'®_data_2; reg_tst_flg <= '0'; fault := '0'; when "01" => Immediate mode if TST = '0' then tag := "001"; 96
97 else tag := "111"; if TRAP = '0' then DDEST <= '0'®_data_2; reg_tst_flg <= '1'; else DDEST(12 downto 0) <= PC; DDEST(28 downto 13) <= (others => '0' DDEST(29) <= '1'; reg_tst_flg <= '0'; data2(31 downto 24) <= tag&berger_code; data2(23 downto 12) <= (others => sign_bit data2(11 downto 0) <= src2; if (RFT = '1' or TRAP = '1') and dest /= "11111" then RFT only reads R31 fault := '1'; TRAP only writes to R31 else fault:='0'; when "10" => Extended immediate mode DDEST <= '0'®_data_2; data2(31 downto 24) <= "010"&berger_code; data2(23 downto 12) <= src2; data2(11 downto 0) <= (others => '0' reg_tst_flg <= '1'; fault := '0'; when others => data2 <= "000"®_data_2; DDEST <= '0'®_data_2; reg_tst_flg <= '0'; fault := '1'; end case; signals if fault = '0' then addr_failure <= '0'; else addr_failure <= '1'; Flag the failure and clear all end process; end beh_imm_xim; Title : Mux_data1 Design : xjobb Author : Andreas Soderberg Company : SP File : mux_data1.vhd Version : 1.0 Date : Rev. by. : Description : Add forward ok flag to ADEST library IEEE; 97
98 use IEEE.std_logic_1164.all; entity MUX_SRC1 is port ( forward_ok : in STD_LOGIC; IN_RDEST : in STD_LOGIC_VECTOR (4 downto 0 RDEST : out STD_LOGIC_VECTOR (5 downto 0) end MUX_SRC1; architecture BEH_MUX_SRC1 of MUX_SRC1 is process (forward_ok, IN_RDEST) is RDEST <= forward_ok&in_rdest; end process; end BEH_MUX_SRC1; Title : Registerbanken Design : xjobb Author : Andreas Soderberg Company : SP File : reg_file.vhd Version : 1.0 Date : Rev. by. : Description : 2x32x33bit block RAM for registers Stores write adresses together with data Disabled by 'check' and 'extra_check' library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_unsigned.all; entity REG_FILE is port ( clk : in STD_LOGIC; addr1 : in STD_LOGIC_VECTOR (4 downto 0 addr2 : in STD_LOGIC_VECTOR (4 downto 0 write_data : in STD_LOGIC_VECTOR (31 downto 0 write_addr : in STD_LOGIC_VECTOR (4 downto 0 check : in STD_LOGIC; extra_check : in STD_LOGIC; data1 : out STD_LOGIC_VECTOR (28 downto 0 data2 : out STD_LOGIC_VECTOR (28 downto 0 end REG_FILE; rbank_failure : out STD_LOGIC architecture BEH_REG_FILE of REG_FILE is type RAM_TYPE is array (31 downto 0) of STD_LOGIC_VECTOR (33 downto 0 signal REG_BANK_A, REG_BANK_B : RAM_TYPE; Use two rwm-arrays for the reg.bank. process (clk, addr1, addr2, write_addr, write_data, check, extra_check, REG_BANK_A, REG_BANK_B) is Read/Write to reg.file variable WE : STD_LOGIC; 98
99 downto 0 variable W_DATA : std_logic_vector (33 downto 0 variable R_DATA1, R_DATA2 : std_logic_vector (33 downto 0 variable r_addr1, r_addr2, w_addr : std_logic_vector (4 end process; end BEH_REG_FILE; if check = '1' then WE := '0'; else WE := '1'; W_DATA := write_addr&write_data(28 downto 0 if extra_check = '1' then w_addr := "00000"; else w_addr := write_addr; if clk'event and clk = '0' then Write on negative edge if WE='1' then REG_BANK_A(conv_integer(w_addr)) <= W_DATA; REG_BANK_B(conv_integer(w_addr)) <= W_DATA; r_addr1:=addr1; r_addr2:=addr2; R_DATA1 := REG_BANK_A(conv_integer(r_addr1) R_DATA2 := REG_BANK_B(conv_integer(r_addr2) data1 <= R_DATA1(28 downto 0 data2 <= R_DATA2(28 downto 0 if (R_DATA1(33 downto 29) /= r_addr1 or R_DATA2(33 downto 29) /= r_addr2) then rbank_failure <= '1'; else rbank_failure <= '0'; Title : EX Design : xjobb Author : Tomas Holmgren Company : SP File : EX.vhd Version : 1.0 Date : Rev. by. : Description : EX library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_arith.all; entity EX is port( 99
100 end EX; CLK : in STD_LOGIC; pulse_in : in std_logic; TSTin : in STD_LOGIC; RST : in STD_LOGIC; clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; OP : in STD_LOGIC_VECTOR (4 downto 0 NEXTOPin : in STD_LOGIC_VECTOR (4 downto 0 X : in STD_LOGIC_VECTOR (28 downto 0 Y : in STD_LOGIC_VECTOR (28 downto 0 A_DESTin : in STD_LOGIC_VECTOR (5 downto 0 D_DESTin : in STD_LOGIC_VECTOR (28 downto 0 wb_tag : in STD_LOGIC_VECTOR (1 downto 0 failure_bus_in : in STD_lOGIC_VECTOR(13 downto 0 failure_bus : out std_logic_vector(13 downto 0 CO : out STD_LOGIC; K : out STD_LOGIC; OV : out STD_LOGIC; TRAP : out STD_LOGIC; TSTout : out STD_LOGIC; CC : out STD_LOGIC_VECTOR (4 downto 0 Q : out STD_LOGIC_VECTOR (31 downto 0 OPout : out STD_LOGIC_VECTOR (4 downto 0 NEXTOPout : out STD_LOGIC_VECTOR (4 downto 0 A_DESTout : out STD_LOGIC_VECTOR (5 downto 0 D_DESTout : out STD_LOGIC_VECTOR (28 downto 0 QC : out STD_LOGIC_VECTOR (4 downto 0 XC : out STD_LOGIC_VECTOR (4 downto 0 ALU_ADDR : out STD_LOGIC_VECTOR (5 downto 0 ALU_DATA : out STD_LOGIC_VECTOR (31 downto 0 YC : out STD_LOGIC_VECTOR (4 downto 0 O_wb_tag : out STD_LOGIC_VECTOR (1 downto 0 pulse_out : out std_logic architecture EX_arch of EX is signal CO_OUT, K_OUT, OV_OUT, TRAP_OUT, BERGER_failure_out : STD_LOGIC; signal o_ex_failure, o_b_ok_out: std_logic; signal CC_OUT, QC_OUT : STD_LOGIC_VECTOR (4 downto 0 signal Q_OUT : STD_LOGIC_VECTOR (28 downto 0 signal i : integer range 0 to 1; type ram is array (0 to 1) of std_logic_vector(4 downto 0 signal old_berger : std_logic_vector(4 downto 0 component ALU port ( A : in STD_LOGIC_VECTOR (23 downto 0 B : in STD_LOGIC_VECTOR (23 downto 0 S : in STD_LOGIC_VECTOR (4 downto 0 CC : out STD_LOGIC_VECTOR (4 downto 0 CO : out STD_LOGIC; K : out STD_LOGIC; OV : out STD_LOGIC; B_OK : out STD_LOGIC; ALU_FAILURE : out STD_LOGIC; Q : out STD_LOGIC_VECTOR (28 downto 0 QC : out STD_LOGIC_VECTOR (4 downto 0 TRAP_OV : out STD_LOGIC end component ; U0 : ALU port map( A => X(23 downto 0), B => Y(23 downto 0), CC => CC_OUT, 100
101 CO => CO_OUT, K => K_OUT, OV => OV_OUT, B_OK => o_b_ok_out, ALU_FAILURE => o_ex_failure, Q => Q_OUT, QC => QC_OUT, S => OP, TRAP_OV => TRAP_OUT ALU_ADDR<=A_DESTin; TSTout <= TSTin; ALU_DATA<="001"&Q_OUT; registers:process(clk, RST, clear_reg, clear_reg2) if RST = '1' or clear_reg = '1' or clear_reg2 = '1' then CO <= '0'; K <= '0'; OV <= '0'; TRAP <= '0'; XC <= "11000"; YC <= "11000"; old_berger <= "11000"; OPout <= (others=>'0' NEXTOPout <= (others=>'0' A_DESTout <= (others=>'0' D_DESTout <= "11"&(26 downto 0 => '0' CC <= "10111"; Q <= "01011"&(26 downto 0 => '0' QC <= "11000"; i <= 0; failure_bus <= (others => '0' pulse_out <= '0'; O_wb_tag <= (others => '1' elsif clk'event and clk='1' then CO <= CO_OUT; K <= K_OUT; OV <= OV_OUT; TRAP <= TRAP_OUT; XC <= X(28 downto 24 YC <= Y(28 downto 24 OPout <= OP; NEXTOPout <= NEXTOPin; A_DESTout <= A_DESTin; D_DESTout <= D_DESTin; CC <= CC_OUT; Q <= "010"&Q_OUT; QC <= QC_OUT; old_berger<= QC_OUT; O_wb_tag <= wb_tag; failure_bus(4 downto 0) <= failure_bus_in(4 downto 0 failure_bus(5) <= o_b_ok_out xor failure_bus_in(5 failure_bus(6) <= o_ex_failure and failure_bus_in(6 failure_bus(13 downto 7) <=failure_bus_in(13 downto 7) ; failure_bus(9 downto 8) <= failure_bus_in(9 downto 8 pulse_out <= pulse_in; end process registers; end EX_arch; Title : ALU Design : xjobb Author : Tomas Holmgren Company : SP 101
102 File : ALU.vhd Version : 1.0 Date : Rev. by. : Description : ALU library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_unsigned.all; entity ALU is port( A : in std_logic_vector (23 downto 0 B : in std_logic_vector (23 downto 0 S : in std_logic_vector (4 downto 0 CO : out std_logic; OV : out std_logic; TRAP_OV : out std_logic; B_OK : out std_logic; ALU_FAILURE : out std_logic; CC : out std_logic_vector (4 downto 0 QC : out std_logic_vector (4 downto 0 K : out std_logic; Q : out std_logic_vector (28 downto 0) end ALU; architecture ALU_arch of ALU is signal ALU_OUT, SHIFT_OUT, MUX_OUT, CC_SHIFT, CC_ALU : std_logic_vector (23 downto 0 signal CO_OUT : std_logic; signal OV_OUT : std_logic; signal B_OUT : std_logic; signal TRAP_OUT : std_logic; signal K_SHIFT : std_logic; signal FAILURE : std_logic; signal CC_OUT : std_logic_vector (4 downto 0 signal QC_OUT : std_logic_vector (4 downto 0 signal ADD_RES : std_logic_vector (48 downto 0 constant ADD : std_logic_vector (4 downto 0) :="00000"; constant SUB : std_logic_vector (4 downto 0) :="00001"; constant ANDA : std_logic_vector (4 downto 0) :="00010"; constant ORA : std_logic_vector (4 downto 0) :="00011"; constant XORA : std_logic_vector (4 downto 0) :="00100"; constant CMP : std_logic_vector (4 downto 0) :="00101"; constant ADDV : std_logic_vector (4 downto 0) :="00110"; constant SUBV : std_logic_vector (4 downto 0) :="00111"; constant LLS : std_logic_vector (4 downto 0) :="01000"; constant LRS : std_logic_vector (4 downto 0) :="01001"; constant ALS : std_logic_vector (4 downto 0) :="01010"; constant ARS : std_logic_vector (4 downto 0) :="01011"; constant BEQ : std_logic_vector (4 downto 0) :="01100"; constant BNE : std_logic_vector (4 downto 0) :="01101"; constant RFT : std_logic_vector (4 downto 0) :="01110"; constant TRAP : std_logic_vector (4 downto 0) :="01111"; constant READ : std_logic_vector (4 downto 0) :="10000"; constant LW : std_logic_vector (4 downto 0) :="10001"; constant PUT : std_logic_vector (4 downto 0) :="10010"; constant SW : std_logic_vector (4 downto 0) :="10011"; constant SGN : std_logic_vector (4 downto 0) :="10100"; constant USGN : std_logic_vector (4 downto 0) :="10101"; 102
103 constant PRT : std_logic_vector (4 downto 0) :="10110"; constant TST : STD_LOGIC_VECTOR (4 downto 0) :="11000"; Instruction SFE = Illegal function count(a: std_logic_vector(2 downto 0)) return std_logic_vector is variable sum : std_logic_vector(1 downto 0 case a is when "000" => sum:="11"; when "001" => sum:="10"; when "010" => sum:="10"; when "011" => sum:="01"; when "100" => sum:="10"; when "101" => sum:="01"; when "110" => sum:="01"; when "111" => sum:="00"; when others => null; end case; return sum; end count; process(a, B, S) variable A_TEMP, B_TEMP, sum : std_logic_vector (23 downto 0 variable carry: std_logic_vector (24 downto 0 variable G, K : std_logic; variable P : std_logic_vector (3 downto 0 case S is when ADD ADDV LW SW READ PUT TRAP RFT PRT TST => A_TEMP := ('0' & A(22 downto 0) B_TEMP := ('0' & B(22 downto 0) K:='0'; when SUB SUBV CMP => A_TEMP := ('0' & A(22 downto 0) B_TEMP := not ('0' & B(22 downto 0) K:='1'; when others => A_TEMP := A; B_TEMP := B; K:='0'; end case; carry(0) := K; for i in 0 to 5 loop for j in 0 to 3 loop P(j):=B_TEMP(j+(i*4)) xor A_TEMP(j+(i*4) G:=B_TEMP(j+(i*4)) and A_TEMP(j+(i*4) sum(j+(i*4)):=p(j) xor carry(j+(i*4) carry(j+(i*4)+1):=g or (P(j) and carry(j+(i*4)) end loop; if (p(0) and p(1) and p(2) and p(3))='1' then carry((i+1)*4):=carry(i*4 end loop; ADD_RES<=carry end process; alu:process (A, B, S, ADD_RES) variable C_TEMP : std_logic; variable CO_TEMP: std_logic; variable K : std_logic; variable A_TEMP : std_logic_vector (23 downto 0 variable B_TEMP : std_logic_vector (23 downto 0 variable TEMP : std_logic_vector (48 downto 0 variable TEMP_R : std_logic_vector (23 downto 0 variable TEMP_C : std_logic_vector (23 downto 0 103
104 A_TEMP := A; B_TEMP := B; TEMP_R := (others => '0' FAILURE <= '0'; TEMP:=ADD_RES; case S is when SUB SUBV CMP => TEMP_R := TEMP(23 downto 0 TEMP_C := not ('0'&TEMP(47 downto 25) CO_TEMP := ((not A(23)) and B(23))or (TEMP_R(23) and ((not A(23)) or B(23)) C_TEMP:=A(23) xor B(23 FAILURE <='0'; when ADD ADDV LW SW READ PUT TRAP RFT PRT TST => TEMP_R := TEMP(23 downto 0 TEMP_C := '1'&TEMP(47 downto 25 CO_TEMP:= (A(23) and B(23))or (TEMP_R(23) and (A(23) or B(23)) C_TEMP:=A(23) xor B(23 FAILURE <='0'; when ANDA => TEMP_R := A_TEMP and B_TEMP; TEMP_C := A_TEMP or B_TEMP; C_TEMP:='0'; CO_TEMP:='0'; FAILURE <='0'; when ORA => TEMP_R := A_TEMP or B_TEMP; TEMP_C := A_TEMP and B_TEMP; C_TEMP:='0'; CO_TEMP:='0'; FAILURE <='0'; when XORA BNE BEQ => TEMP_R := A_TEMP xor B_TEMP; TEMP_C := A_TEMP and B_TEMP; C_TEMP:='0'; CO_TEMP:='0'; FAILURE <='0'; when LLS LRS ALS ARS SGN USGN => TEMP_R := (others=>'0' TEMP_C := (others=>'0' C_TEMP:='0'; CO_TEMP:='0'; FAILURE <='0'; when others => TEMP_R := (others=>'0' TEMP_C := (others=>'0' C_TEMP:='0'; CO_TEMP:='0'; FAILURE <='1'; end case; if (S=BNE and not(temp_r=" ")) or S=TRAP or S=RFT then B_OUT <= '1'; elsif S= BEQ and (TEMP_R=" ") then B_OUT <= '1'; else B_OUT <= '0'; if S = ADDV or S = SUBV then TRAP_OUT <= CO_TEMP xor TEMP_R(23 else TRAP_OUT <= '0'; 104
105 ALU_OUT <=(C_TEMP xor TEMP_R(23)) & TEMP_R(22 downto 0 CC_ALU <= TEMP_C; CO_OUT <= CO_TEMP; OV_OUT <= CO_TEMP xor TEMP_R(23 end process alu; Shift:process (A, B, S) variable C_TEMP, SignVector, B_TEMP, A_TEMP : std_logic_vector(23 downto 0 variable sign : std_logic; if S = ARS then sign:='1'; A_TEMP := A; B_TEMP := B; C_TEMP :=(others => '1' K_SHIFT <= A_TEMP(23 else sign:='0'; K_SHIFT <= '0'; A_TEMP := A; B_TEMP := B; C_TEMP :=(others => '1' if S = LRS or S = ARS then shift right if B_TEMP>="11000" then SignVector := (others => A_TEMP(23) and sign C_TEMP := not (A_TEMP xor SignVector A_TEMP := (others => (A_TEMP(23) and sign) else for i in 0 to 3 loop if B_TEMP(i) = '1' then C_TEMP(2**(i+1)-2 downto (2**i)-1) := (others => A_TEMP(23) and sign C_TEMP(2**(i+1)-2 downto (2**i)-1) := not(a_temp((2**i)-1 downto 0) xor C_TEMP(2**(i+1)-2 downto (2**i)-1) A_TEMP := (23 downto 24-(2**i) => (A_TEMP(23))) & A_TEMP(23 downto (2**i) end loop; i if B_TEMP(4) = '1' then C_TEMP(22 downto 7) := (others => A_TEMP(23) and sign C_TEMP(22 downto 7) := not(a_temp(15 downto 0) xor C_TEMP(22 downto 7) A_TEMP := (23 downto 8 => (A_TEMP(23))) & A_TEMP(23 downto 16 else shift left if B_TEMP>="11000" then C_TEMP := not A_TEMP; A_TEMP := (others => '0' else for i in 0 to 3 loop if B_TEMP(i) = '1' then C_TEMP((2**(i+1)-2) downto (2**i)-1) := not A_TEMP(23 downto 24-(2**i) A_TEMP := A_TEMP((23-(2**i)) downto 0) & ((2**i)-1 downto 0 => '0' end loop; i if B_TEMP(4) = '1' then C_TEMP(22 downto 7) := not A_TEMP(23 downto 8 A_TEMP := A_TEMP(7 downto 0) & (15 downto 0 => '0' CC_SHIFT <= C_TEMP; 105
106 SHIFT_OUT <= A_TEMP; end process Shift; mux:process(shift_out, ALU_OUT, S) if S = LLS or S = LRS or S = ALS or S = ARS then MUX_OUT<= SHIFT_OUT; else MUX_OUT<= ALU_OUT; end process mux; counter:process(cc_shift, CC_ALU, S) variable MUX_OUT : std_logic_vector (23 downto 0 variable s7, s6, s5, s4, s3, s2,s1, s0 : STD_LOGIC_VECTOR (1 downto 0 variable tmp : std_logic_vector(4 downto 0 if S = LLS or S = LRS or S = ALS or S = ARS then MUX_OUT := CC_SHIFT; else MUX_OUT := CC_ALU; s0:= count(mux_out(2 downto 0) s1:= count(mux_out(5 downto 3) s2:= count(mux_out(8 downto 6) s3:= count(mux_out(11 downto 9) s4:= count(mux_out(14 downto 12) s5:= count(mux_out(17 downto 15) s6:= count(mux_out(20 downto 18) s7:= count(mux_out(23 downto 21) tmp := "00000"; tmp := tmp + s7; tmp := tmp + s6; tmp := tmp + s5; tmp := tmp + s4; tmp := tmp + s3; tmp := tmp + s2; tmp := tmp + s1; tmp := tmp + s0; CC_OUT<= tmp; s7+s6+s5+s4+s3+s2+s1+s0; end process counter; berger:process (MUX_OUT) variable s7, s6, s5, s4, s3, s2,s1, s0 : STD_LOGIC_VECTOR (1 downto 0 variable tmp : std_logic_vector(4 downto 0 s0:= count(mux_out(2 downto 0) s1:= count(mux_out(5 downto 3) s2:= count(mux_out(8 downto 6) s3:= count(mux_out(11 downto 9) s4:= count(mux_out(14 downto 12) s5:= count(mux_out(17 downto 15) s6:= count(mux_out(20 downto 18) s7:= count(mux_out(23 downto 21) tmp := "00000"; tmp := tmp + s7; tmp := tmp + s6; tmp := tmp + s5; tmp := tmp + s4; tmp := tmp + s3; tmp := tmp + s2; tmp := tmp + s1; tmp := tmp + s0; QC_OUT<= tmp; s7+s6+s5+s4+s3+s2+s1+s0; QC_OUT<=s7+s6+s5+s4+s3+s2+s1+s0; end process berger; process(s, MUX_OUT, QC_OUT) 106
107 end ALU_arch; if S=CMP then if MUX_OUT(23)='1' then Q<=" "; else Q<=" "; else Q<=QC_OUT&MUX_OUT; end process; TRAP_OV <= TRAP_OUT; CO <= CO_OUT; OV <= OV_OUT; CC <= CC_OUT; K <= K_SHIFT; QC <= QC_OUT; B_OK <= B_OUT; ALU_FAILURE <= FAILURE; Title : BC Design : xjobb Author : Tomas Holmgren/Andreas Soderberg Company : SP File : bp.vhd Version : 1.0 Date : Rev. by. : Description : Delays one cycle Make second berger comparison library IEEE; use IEEE.std_logic_1164.all; entity BP is port ( clk : in STD_LOGIC; reset : in STD_LOGIC; b2f_in : in std_logic; clear_reg : in std_logic; clear_reg2 : in std_logic; ov_in : in std_logic; pulse_in : in std_logic; trap_in : in std_logic; TSTin : in STD_LOGIC; res_in : in std_logic_vector(31 downto 0 a_dest_in : in std_logic_vector(5 downto 0 d_dest_in : in std_logic_vector(28 downto 0 op_in : in std_logic_vector(4 downto 0 nop_in : in std_logic_vector(4 downto 0 f_bus_in : in std_logic_vector(13 downto 0 berger_in : in std_logic_vector(4 downto 0 berger_ex : in std_logic_vector(4 downto 0 wb_tag : in std_logic_vector(1 downto 0 ov_out TSTout pulse_out trap_out : out std_logic; : out STD_LOGIC; : out std_logic; : out std_logic; 107
108 end BP; O_wb_tag : out std_logic_vector(1 downto 0 res_out : out std_logic_vector(31 downto 0 a_dest_out : out std_logic_vector(5 downto 0 d_dest_out : out std_logic_vector(28 downto 0 op_out : out std_logic_vector(4 downto 0 nop_out : out std_logic_vector(4 downto 0 f_bus_out : out std_logic_vector(13 downto 0) architecture BP_arch of BP is signal b1f : std_logic; process (berger_in, berger_ex) if berger_ex = berger_in then b1f <= '0'; else b1f <= '1'; end process; process (clk,reset, clear_reg, clear_reg2) if reset='1' or clear_reg = '1' or clear_reg2 = '1' then pulse_out <= '1'; trap_out <= '0'; ov_out <= '0'; TSTout <= '0'; res_out <= " "&(23 downto 0=>'0' a_dest_out <= (others=>'0' d_dest_out <= (others=>'0' f_bus_out <= (others=>'0' op_out <= (others=>'0' nop_out <= (others=>'0' O_wb_tag <= (others=>'1' elsif clk'event and clk='1' then TSTout <= TSTin; pulse_out <= pulse_in; trap_out <= trap_in; res_out <= "011"&res_in(28 downto 0 a_dest_out <= a_dest_in; d_dest_out <= d_dest_in; f_bus_out(6 downto 0) <= f_bus_in(6 downto 0 f_bus_out(7) <= b2f_in; f_bus_out(8) <= b1f; f_bus_out(13 downto 9)<= f_bus_in(13 downto 9 ov_out <= ov_in; op_out <= op_in; nop_out <= nop_in; end process; end BP_arch; O_wb_tag <= wb_tag; Title : WB Design : xjobb Author : Tomas Holmgren Company : SP File : WB.vhd Version : 1.0 Date :
109 Rev. by. : Description : WB library IEEE; use IEEE.STD_LOGIC_1164.all; entity WB is port ( pulse_in : in STD_LOGIC; CLK : in STD_LOGIC; RST : in STD_LOGIC; clear_reg : in STD_LOGIC; clear_reg2 : in STD_LOGIC; OV : in STD_LOGIC; TSTin : in STD_LOGIC; TRAP : in STD_LOGIC; reg_disable : in STD_LOGIC; reg_disable2 : in STD_LOGIC; wb_tag : in STD_LOGIC_VECTOR (1 downto 0 NEXTOP : in STD_LOGIC_VECTOR (4 downto 0 A_DEST : in STD_LOGIC_VECTOR (5 downto 0 RES : in STD_LOGIC_VECTOR (28 downto 0 D_DEST : in STD_LOGIC_VECTOR (28 downto 0 DATA_IOin : in STD_LOGIC_VECTOR (28 downto 0 OP : in STD_LOGIC_VECTOR (4 downto 0 failure_bus_in : in STD_LOGIC_VECTOR (13 downto 0 DATA_DM_in : in STD_LOGIC_VECTOR (31 downto 0 end WB; TSTout : out STD_lOGIC; PRI : out STD_LOGIC; WEinv : out STD_LOGIC; OEinv : out STD_LOGIC; IO_RW : out STD_LOGIC; ex_trap : out STD_LOGIC; pulse_out : out STD_LOGIC; io_select : out STD_LOGIC; io_wr : out STD_LOGIC; disable : buffer STD_LOGIC; A_DESTout : out STD_LOGIC_VECTOR (4 downto 0 failure_bus : out STD_LOGIC_VECTOR (13 downto 0 ADDR_DM : out STD_LOGIC_VECTOR (19 downto 0 D_DESTout : out STD_LOGIC_VECTOR (31 downto 0 DATA_IOout : out STD_LOGIC_VECTOR (11 downto 0 IODDR : out STD_LOGIC_VECTOR (11 downto 0 IOPRI : out STD_LOGIC_VECTOR (11 downto 0 DATA_DM_out : out STD_LOGIC_VECTOR (31 downto 0) architecture WB_arch of WB is signal counter : integer range 0 to 7; signal WB_failure_out : STD_LOGIC; signal WEinv_out : STD_LOGIC; signal USE_OUT : STD_LOGIC; signal SET_PRI : STD_LOGIC; signal RW_OUT : STD_LOGIC; signal NEXTOP_temp : STD_LOGIC_VECTOR (4 downto 0 signal DATAout : STD_LOGIC_VECTOR (30 downto 0 signal DATA_DMtemp : STD_LOGIC_VECTOR (28 downto 0 signal temp : STD_LOGIC_VECTOR (7 downto 0 signal mux_failure1 : STD_LOGIC; signal mux_failure2 : STD_LOGIC; signal remove_disable : std_logic; signal io_wr_int : std_logic; 109
110 signal io_select_int : std_logic; constant ADD : STD_LOGIC_VECTOR (4 downto 0) :="00000"; constant SUB : STD_LOGIC_VECTOR (4 downto 0) :="00001"; constant ANDA : STD_LOGIC_VECTOR (4 downto 0) :="00010"; constant ORA : STD_LOGIC_VECTOR (4 downto 0) :="00011"; constant XORA : STD_LOGIC_VECTOR (4 downto 0) :="00100"; constant CMP : STD_LOGIC_VECTOR (4 downto 0) :="00101"; constant ADDV : STD_LOGIC_VECTOR (4 downto 0) :="00110"; constant SUBV : STD_LOGIC_VECTOR (4 downto 0) :="00111"; constant LLS : STD_LOGIC_VECTOR (4 downto 0) :="01000"; constant LRS : STD_LOGIC_VECTOR (4 downto 0) :="01001"; constant ALS : STD_LOGIC_VECTOR (4 downto 0) :="01010"; constant ARS : STD_LOGIC_VECTOR (4 downto 0) :="01011"; constant BEQ : STD_LOGIC_VECTOR (4 downto 0) :="01100"; constant BNE : STD_LOGIC_VECTOR (4 downto 0) :="01101"; constant RFT : STD_LOGIC_VECTOR (4 downto 0) :="01110"; constant TRAPA: STD_LOGIC_VECTOR (4 downto 0) :="01111"; constant READ : STD_LOGIC_VECTOR (4 downto 0) :="10000"; constant LW : STD_LOGIC_VECTOR (4 downto 0) :="10001"; constant PUT : STD_LOGIC_VECTOR (4 downto 0) :="10010"; constant SW : STD_LOGIC_VECTOR (4 downto 0) :="10011"; constant SGN : STD_LOGIC_VECTOR (4 downto 0) :="10100"; constant USGN : STD_LOGIC_VECTOR (4 downto 0) :="10101"; constant PRT : STD_LOGIC_VECTOR (4 downto 0) :="10110"; constant TST : STD_LOGIC_VECTOR (4 downto 0) :="11000"; dm:process(op, DATA_DM_in, D_DEST, RES, disable) if disable='1' then WEinv_out<='1'; OEinv<='1'; ADDR_DM<=RES(19 downto 0 DATA_DM_out<=(others=>'0' DATA_DMtemp<=(others=>'0' elsif OP=LW then WEinv_out<='1'; OEinv<='0'; ADDR_DM<=RES(19 downto 0 DATA_DM_out<=(others=>'0' DATA_DMtemp<=DATA_DM_in(28 downto 0 elsif OP=SW then OEinv<='1'; WEinv_out<='0'; ADDR_DM<=RES(19 downto 0 DATA_DM_out<="000"&D_DEST; DATA_DMtemp<=(others=>'0' else WEinv_out<='1'; OEinv<='1'; DATA_DM_out<=(others=>'0' ADDR_DM<=RES(19 downto 0 DATA_DMtemp<=(others=>'0' end process dm; WE:process(OP, CLK) if (OP=SW and CLK='1') then WEinv<='0'; else WEinv<='1'; end process WE; Tristate:process(WEinv_out,DATAtristate) if WEinv_out='0' then DATA_DM<=DATAtristate; 110
111 else DATA_DM<=(others =>'Z' end process Tristate; mux:process(op, RES, D_DEST, DATA_DMtemp, DATA_IOin ) case (OP) is when LW TST => DATAout<= "00"&DATA_DMtemp; when SW TRAPA PRT BEQ BNE PUT => DATAout<= "01"&D_DEST; when READ => DATAout<= "10"&DATA_IOin; when others => DATAout<= "11"&RES; end case; end process mux; process(dataout, OP, wb_tag) variable mux_id : std_logic_vector (1 downto 0 case (OP) is when LW => mux_id := "00"; when SW TRAPA PRT BEQ BNE PUT => mux_id := "01"; when READ => mux_id := "10"; when others => mux_id := "11"; end case; end process; if mux_id /= DATAout(30 downto 29) then Comparator 1 mux_failure1 <= '1'; else mux_failure1 <= '0'; if DATAout(30 downto 29) /= wb_tag then Comparator 2 mux_failure2 <= '1'; else mux_failure2 <= '0'; Failure:process(OP, NEXTOP_temp, A_DEST, RST) if ((NEXTOP_temp/=OP and OP/=TRAPA) or (A_DEST="011111" and OP/=TRAPA)) and (RST = '0') then WB_failure_out<='1'; else WB_failure_out<='0'; end process Failure; IO:process(OP, disable) case OP is when PUT => io_select_int <='0'; io_wr_int <= '0'; RW_OUT<='1'; SET_PRI <= '0'; when PRT => io_select_int <='1'; io_wr_int <= '0'; RW_OUT<='0'; 111
112 SET_PRI <= '1'; when READ => io_select_int <='0'; io_wr_int <= '1'; RW_OUT<='0'; SET_PRI <= '0'; when others=> io_select_int <='1'; io_wr_int <= '0'; RW_OUT<='0'; SET_PRI <= '0'; end case; if disable='1' then io_select_int <='1'; io_wr_int <= '0'; RW_OUT<='0'; SET_PRI <= '0'; end process IO; remove_disable <= reg_disable or reg_disable2; disable_wb:process(failure_bus_in,mux_failure1,mux_failure2,wb_fai lure_out, reg_disable, TSTin) variable bus_failure, tot_failure : std_logic; if (wb_failure_out/='0')(mux_failure1&mux_failure2&failure_bus_in(11 downto 10)&WB_failure_out&failure_bus_in(8 downto 0)/=" ") and TSTin='0' then if (failure_bus_in(11 downto 10) /= "00") or (failure_bus_in(8 downto 0)/=" ") then bus_failure := '1'; else bus_failure := '0'; tot_failure := bus_failure or WB_failure_out or mux_failure1 or mux_failure2 or TSTin; end process disable_wb; io_select <= io_select_int; io_wr <= io_wr_int; IO_RW <= RW_OUT; DATA_IOout <= RES(11 downto 0 IOPRI <= RES(11 downto 0 IODDR <= D_DEST(11 downto 0 PRI <= SET_PRI; registers:process(clk, RST, clear_reg, clear_reg2) if RST = '1' or clear_reg = '1' or clear_reg2 = '1' then NEXTOP_temp <= (others => '0' IO_RW <= '0'; TSTout <= '0'; DATA_IOout <= (others => '0' IODDR<= (others => '0' IOPRI <= (others => '0' D_DESTout <= "10011"&(26 downto 0 => '0' A_DESTout <= (others => '0' failure_bus(8 downto 0) <= (others => '0' failure_bus(9) <= '0'; failure_bus(13 downto 10)<= (others => '0' pulse_out <= '0'; PRI <= '0'; ex_trap <= '0'; io_select <= '1'; io_wr <= '1'; elsif clk'event and clk='1' then TSTout <= TSTin; pulse_out <= pulse_in; 112
113 end WB_arch; NEXTOP_temp <= NEXTOP; failure_bus(8 downto 0) <= failure_bus_in(8 downto 0 failure_bus(9) <= WB_failure_out; failure_bus(11 downto 10) <= failure_bus_in(11 downto 10 failure_bus(12) <= failure_bus_in(12) or mux_failure2; failure_bus(13) <= mux_failure1; IO_RW <= RW_OUT; DATA_IOout <= RES(11 downto 0 IOPRI <= RES(11 downto 0 IODDR <= D_DEST(11 downto 0 D_DESTout <= "100"&DATAout(28 downto 0 A_DESTout <= A_DEST(4 downto 0 io_select <= io_select_int; io_wr <= io_wr_int; PRI <= SET_PRI; ex_trap <= TRAP; end process registers; Title : IOport A Design : xjobb Author : Andreas Soderberg Company : SP File : ioport.vhd Version : 1.0 Date : Rev. by. : Tomas Holmgren Description : IOport with READ, PUT, PRT library IEEE; use IEEE.STD_LOGIC_1164.all; entity IOport is port ( reset : in STD_LOGIC; use_io : in STD_LOGIC; safe_state : in STD_LOGIC; safe_state2 : in STD_LOGIC; safe_state3 : in STD_LOGIC; RW : in STD_LOGIC; IO_out : in STD_LOGIC_VECTOR (11 downto 0 DDR : in STD_LOGIC_VECTOR (11 downto 0 IO_in : out STD_LOGIC_VECTOR (11 downto 0 IO_port : inout STD_LOGIC_VECTOR (11 downto 0) end IOport; architecture IOport_arch of IOport is signal port_data : STD_LOGIC_VECTOR (11 downto 0 signal reg_ddr : STD_LOGIC_VECTOR (11 downto 0 put_prt: process(reset, use_io, DDR, RW, IO_out, safe_state, safe_state2, safe_state3, port_data) variable FD_RW : STD_LOGIC; if reset='1' then 113
114 register) else port_data <= (others=>'0' reg_ddr <= (others=>'0' if use_io='1' then reg_ddr <= DDR; PRT configure DDR(data direction if safe_state ='1' or safe_state2='1' or safe_state3 = '1' then port_data<=(others => '0' if safestate set all dataout to '0' elsif RW='1' then PUT for i in 0 to 11 loop if DDR(i) = '0' then Mask port_data(i)<=io_out(i end loop; port_data(11 downto 4)<=IO_out(11 downto 4 end process put_prt; read:process(io_port, reg_ddr, port_data) IO_in<=((not reg_ddr) and IO_port) or (reg_ddr and port_data READ IO_in <= port_data(11 downto 4)&IO_port(3 downto 0 end process read; tristate: process(port_data, reg_ddr) for i in 0 to 11 loop if reg_ddr(i) = '0' then Port = input IO_port(i) <= '0'; else Port = output IO_port(i) <= port_data(i IO_port(11 downto 4) <= port_data(11 downto 4 IO_port(3 downto 0) <=(others => 'Z' end loop; end process tristate; end IOport_arch; Title : IOportB Design : xjobb Author : Andreas Soderberg Company : SP File : ioportb.vhd Version : 1.0 Date : Rev. by. : Tomas Holmgren Description : Reads/stores data on pin n depending on DDR. DDR is configured by PRT by 'use_io'. 'Conf_DDR' configures DDR in IO port c. When safe-state => all outputs = 0 library IEEE; 114
115 use IEEE.std_logic_1164.all; entity IOportB is port ( reset : in STD_LOGIC; use_io : in STD_LOGIC; safe_state : in STD_LOGIC; safe_state2 : in STD_LOGIC; safe_state3 : in STD_LOGIC; RW : in STD_LOGIC; IO_out : in STD_LOGIC_VECTOR (11 downto 0 DDR : in STD_LOGIC_VECTOR (11 downto 0 end IOportB; conf_ddr : out STD_LOGIC; IO_in : out STD_LOGIC_VECTOR (11 downto 0 IO_port : inout STD_LOGIC_VECTOR (11 downto 0) architecture IOport_arch of IOportB is signal port_data : STD_LOGIC_VECTOR (11 downto 0 signal reg_ddr : STD_LOGIC_VECTOR (11 downto 0 conf_ddr <= use_io; put_prt: process(reset, use_io, DDR, RW, IO_out, safe_state, safe_state2, safe_state3, port_data) variable FD_RW : STD_LOGIC; if reset='1' then port_data <= (others=>'0' reg_ddr <= (others=>'0' else direction register) if use_io='1' then PRT reg_ddr <= DDR; configure DDR(data if safe_state ='1' or safe_state2='1' or safe_state3 = '1' then port_data<=(others => '0' if safestate set all dataout to '0' elsif RW='1' then PUT for i in 0 to 11 loop if DDR(i) = '0' then Mask port_data(i)<=io_out(i end loop; end process put_prt; read:process(io_port, reg_ddr, port_data) IO_in<=((not reg_ddr) and IO_port) or (reg_ddr and port_data READ IO_in <= port_data(11 downto 4)&IO_port(3 downto 0 end process read; tristate: process(port_data, use_io, DDR), reg_ddr if use_io='1' then IO_port<= DDR; else for i in 0 to 11 loop if reg_ddr(i) = '0' then Port = input IO_port(i) <= '0'; else Port = output 115
116 end IOport_arch; IO_port(i) <= port_data(i IO_port(11 downto 4) <= port_data(11 downto 4 IO_port(3 downto 0) <=(others => 'Z' end loop; end process tristate; Title : IO_CMP Design : xjobb Author : Andreas Soderberg Company : SP File : io_cmp.vhd Version : 1.0 Date : Rev. by. : Tomas Holmgren Description : IOport with READ, PUT, PRT library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_unsigned.all; entity IO_CMP is port ( reset : in std_logic; set_pri : in std_logic; priority : in std_logic_vector (11 downto 0 IOa : in STD_LOGIC_VECTOR (11 downto 0 IOb : in STD_LOGIC_VECTOR (11 downto 0 IO_in : out STD_LOGIC_VECTOR(28 downto 0) end IO_CMP; architecture IO_CMP of IO_CMP is signal PRI_reg : std_logic_vector(11 downto 0 function count(a: std_logic_vector(2 downto 0)) return std_logic_vector is variable sum : std_logic_vector(1 downto 0 case a is when "000" => sum:="11"; when "001" => sum:="10"; when "010" => sum:="10"; when "011" => sum:="01"; when "100" => sum:="10"; when "101" => sum:="01"; when "110" => sum:="01"; when "111" => sum:="00"; when others => null; end case; return sum; end count; process(set_pri) if set_pri'event and set_pri='1' then PRI_reg <= priority; 116
117 end process; process(reset,ioa, IOb, PRI_reg) variable berger_tmp:std_logic_vector(4 downto 0 variable tmp : std_logic_vector(23 downto 0 variable s7, s6, s5, s4, s3, s2,s1, s0 : STD_LOGIC_VECTOR (1 downto 0 if reset='1' then IO_in <=(others=>'0' else for i in 0 to 11 loop if PRI_reg(i) = '0' then tmp(i) := IOa(i) and not IOb(i tmp(i+12) := IOa(i) xor IOb(i else tmp(i) := IOa(i) and IOb(i tmp(i+12) :=not (IOa(i) xor IOb(i) end loop; s0:= count(tmp(2 downto 0) s1:= count(tmp(5 downto 3) s2:= count(tmp(8 downto 6) s3:= count(tmp(11 downto 9) s4:= count(tmp(14 downto 12) s5:= count(tmp(17 downto 15) s6:= count(tmp(20 downto 18) s7:= count(tmp(23 downto 21) berger_tmp := "00000"; berger_tmp := berger_tmp + s7; berger_tmp := berger_tmp + s6; berger_tmp := berger_tmp + s5; berger_tmp := berger_tmp + s4; berger_tmp := berger_tmp + s3; berger_tmp := berger_tmp + s2; berger_tmp := berger_tmp + s1; berger_tmp := berger_tmp + s0; IO_in <= berger_tmp&tmp; end process; end IO_CMP; Title : FAULT Design : xjobb Author : Tomas Holmgren Company : SP File : fault.vhd Version : 1.0 Date : Rev. by. : Description : Statemachine which checks failurebus library IEEE; use IEEE.std_logic_1164.all; entity FAULT is port ( failure_bus : in STD_LOGIC_VECTOR (13 downto 0 clk : in STD_LOGIC; reset : in STD_LOGIC; 117
118 end FAULT; TST : in STD_LOGIC; reset_bus : out STD_LOGIC_VECTOR (4 downto 0 retry : out STD_LOGIC; reg_disable : out STD_LOGIC; safe : out STD_LOGIC architecture FAULT_arch of FAULT is type state_type is(vila, wait_state, safe_state, wait_tst_state, tst_state signal state : state_type; signal count, counted : STD_LOGIC; process(clk, reset) variable temp_failure: STD_LOGIC_VECTOR (13 downto 0 if reset='1' then state<=vila; reset_bus<="00000"; retry<='0'; reg_disable<='1'; temp_failure:=" "; safe<='0'; count<='0'; elsif clk'event and clk='1' then case state is when vila => if (temp_failure and failure_bus)=" " then if failure_bus(0)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(1)='1' and TST = '0' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(1)='1' and TST = '1' then temp_failure:=" "; reset_bus<="00000"; retry<='0'; state<=wait_tst_state; reg_disable<='0'; elsif failure_bus(2)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(3)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(4)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(5)='1' then temp_failure:=" "; reset_bus<="01111"; 118
119 else retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(6)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(7)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(8)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(9)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(10)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(11)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(12)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; elsif failure_bus(13)='1' then temp_failure:=" "; reset_bus<="01111"; retry<='1'; state<=wait_state; reg_disable<='1'; else temp_failure:=" "; reset_bus<="00000"; retry<='0'; reg_disable<='0'; safe<='1'; reset_bus<="11111"; retry<='0'; state<=safe_state; when wait_state => if counted='1' then state<=vila; count<='0'; else count<='1'; reset_bus<="00000"; 119
120 retry<='0'; reg_disable<='1'; when wait_tst_state => if failure_bus /= " " then state <= safe_state; reg_disable<='1'; else state <= tst_state; reg_disable<='1'; when tst_state => if failure_bus /= " " then state <= safe_state; reg_disable<='1'; else state <= vila; reg_disable<='0'; when safe_state => safe<='1'; reset_bus<="11111"; retry<='0'; reg_disable<='1'; when others => state<=safe_state; end case; end process; process(clk, reset) variable counter : integer range 0 to 6; if reset='1' then counter:=0; counted<='0'; elsif clk'event and clk='1' then if count='1' then counter:= counter+1; counted<='0'; else counter:=0; if counter=4 then counted<='1'; end process; end FAULT_arch; 120
121 Bilaga 14 VHDL-kod för Krets 2 Title : KRETS2 Design : xjobb Author : - Company : SP File : KRETS2.vhd Version : 1.0 Date : Rev. by. : Description : Sammankoppling av blocken i krets 2 library IEEE; use IEEE.std_logic_1164.all; entity KRETS2 is port( CLK : in STD_LOGIC; CO : in STD_LOGIC; K : in STD_LOGIC; PULSE : in STD_LOGIC; RESET : in STD_LOGIC; TST : in STD_LOGIC; conf_ddr : in STD_LOGIC; CC : in STD_LOGIC_VECTOR (4 downto 0 FAILUREBUS : in STD_LOGIC_VECTOR (13 downto 0 OP : in STD_LOGIC_VECTOR (4 downto 0 QC : in STD_LOGIC_VECTOR (4 downto 0 XC : in STD_LOGIC_VECTOR (4 downto 0 YC : in STD_LOGIC_VECTOR (4 downto 0 B2F_OUT : out STD_LOGIC; DISABLE : out STD_LOGIC; PULSE_OUT : out STD_LOGIC; RETRY : out STD_LOGIC; SAFE : out STD_LOGIC; BERGER_OUT : out STD_LOGIC_VECTOR (4 downto 0 CLEAR_REG : out STD_LOGIC_VECTOR (4 downto 0 IO_B_in : inout STD_LOGIC_VECTOR (11 downto 0 IO_B_out : inout STD_LOGIC_VECTOR (11 downto 0) end KRETS2; architecture KRETS2_arch of KRETS2 is signal SAFEX : STD_LOGIC ; signal NET499 : STD_LOGIC ; signal NET515 : STD_LOGIC ; component BERGER_PREDICTION port ( BERGERin : in STD_LOGIC_VECTOR (4 downto 0 CC : in STD_LOGIC_VECTOR (4 downto 0 CO : in STD_LOGIC; K : in STD_LOGIC; S : in STD_LOGIC_VECTOR (4 downto 0 XC : in STD_LOGIC_VECTOR (4 downto 0 YC : in STD_LOGIC_VECTOR (4 downto 0 BERGER_failure : out STD_LOGIC; BERGERout : out STD_LOGIC_VECTOR (4 downto 0) 121
122 end component ; component FAULT port ( TST : in STD_LOGIC; clk : in STD_LOGIC; failure_bus : in STD_LOGIC_VECTOR (13 downto 0 reset : in STD_LOGIC; reg_disable : out STD_LOGIC; reset_bus : out STD_LOGIC_VECTOR (4 downto 0 retry : out STD_LOGIC; safe : out STD_LOGIC end component ; component IOPORTC port ( conf_ddr : in STD_LOGIC; reset : in STD_LOGIC; safe_pulse : in STD_LOGIC; safe_state : in STD_LOGIC; IOin : inout STD_LOGIC_VECTOR (11 downto 0 IOout : inout STD_LOGIC_VECTOR (11 downto 0) end component ; component PULSE_COUNTER port ( clk : in STD_LOGIC; pulse : in STD_LOGIC; reset : in STD_LOGIC; safe_state : out STD_LOGIC end component ; U0 : BERGER_PREDICTION port map( BERGER_failure => B2F_OUT, BERGERin => QC, BERGERout => BERGER_OUT, CC => CC, CO => CO, K => K, S => OP, XC => XC, YC => YC U1 : FAULT port map( TST => TST, clk => CLK, failure_bus => FAILUREBUS, reg_disable => DISABLE, reset => RESET, reset_bus => CLEAR_REG, retry => RETRY, safe => SAFEX U2 : IOPORTC port map( IOin => IO_B_in, IOout => IO_B_out, conf_ddr => conf_ddr, reset => RESET, safe_pulse => NET499, 122
123 safe_state => SAFEX U3 : PULSE_COUNTER port map( clk => CLK, pulse => PULSE, reset => RESET, safe_state => NET499 PULSE_OUT <= PULSE; SAFE <= SAFEX; end KRETS2_arch; Title : BERGERKODSPREDIKTOR Design : xjobb Author : Tomas Holmgren Company : SP File : BERGER_prediction.vhd Version : 1.0 Date : Rev. by. : Description : Predicts Bergercode to the result generated in the ALU library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_unsigned.all; entity BERGER_prediction is port ( CO K : in STD_LOGIC; : in STD_LOGIC; S : in STD_LOGIC_VECTOR (4 downto 0 BERGERin : in STD_LOGIC_VECTOR (4 downto 0 XC : in STD_LOGIC_VECTOR (4 downto 0 YC : in STD_LOGIC_VECTOR (4 downto 0 CC : in STD_LOGIC_VECTOR (4 downto 0 BERGER_failure : out STD_LOGIC; BERGERout : out STD_LOGIC_VECTOR (4 downto 0) end BERGER_prediction; architecture BERGER_prediction_arch of BERGER_prediction is signal failure_out : STD_LOGIC; signal RESout : STD_LOGIC_VECTOR (28 downto 0 signal Rout : STD_LOGIC_VECTOR (4 downto 0 constant ADD : std_logic_vector (4 downto 0) :="00000"; constant SUB : std_logic_vector (4 downto 0) :="00001"; constant ANDA : std_logic_vector (4 downto 0) :="00010"; constant ORA : std_logic_vector (4 downto 0) :="00011"; constant XORA : std_logic_vector (4 downto 0) :="00100"; constant CMP : std_logic_vector (4 downto 0) :="00101"; constant ADDV : std_logic_vector (4 downto 0) :="00110"; constant SUBV : std_logic_vector (4 downto 0) :="00111"; constant LLS : std_logic_vector (4 downto 0) :="01000"; 123
124 constant LRS : std_logic_vector (4 downto 0) :="01001"; constant ALS : std_logic_vector (4 downto 0) :="01010"; constant ARS : std_logic_vector (4 downto 0) :="01011"; constant BEQ : std_logic_vector (4 downto 0) :="01100"; constant BNE : std_logic_vector (4 downto 0) :="01101"; constant RFT : std_logic_vector (4 downto 0) :="01110"; constant TRAP : std_logic_vector (4 downto 0) :="01111"; constant READ : std_logic_vector (4 downto 0) :="10000"; constant LW : std_logic_vector (4 downto 0) :="10001"; constant PUT : std_logic_vector (4 downto 0) :="10010"; constant SW : std_logic_vector (4 downto 0) :="10011"; constant SGN : std_logic_vector (4 downto 0) :="10100"; constant USGN : std_logic_vector (4 downto 0) :="10101"; constant PRT : std_logic_vector (4 downto 0) :="10110"; constant TST : STD_LOGIC_VECTOR (4 downto 0) :="11000"; prediction:process (XC, YC, CC, K, S, BERGERin, CO) variable XC_TEMP : STD_LOGIC_VECTOR (4 downto 0 variable YC_TEMP : STD_LOGIC_VECTOR (4 downto 0 variable CC_TEMP : STD_LOGIC_VECTOR (4 downto 0 variable R : STD_LOGIC_VECTOR (4 downto 0 variable gamma : STD_LOGIC_VECTOR (1 downto 0 case(s) is when SUB SUBV CMP => XC_TEMP := XC; YC_TEMP := not YC; CC_TEMP := CC; if CO='0' then gamma := "10"; else gamma := "00"; when ADD ADDV LW SW READ PUT TRAP RFT PRT TST => XC_TEMP := XC; YC_TEMP := YC; CC_TEMP := not CC; if CO='1' then gamma := "10"; else gamma := "00"; when ANDA ORA => XC_TEMP := XC; YC_TEMP := YC; gamma := "01"; CC_TEMP := not CC; when XORA BNE BEQ => XC_TEMP := XC; YC_TEMP := YC; gamma := "10"; CC_TEMP := not CC(3 downto 0)&'0'+"11000"; when LLS LRS ALS => XC_TEMP := XC; YC_TEMP := (others=>'0' gamma := "00" ; CC_TEMP := CC; when ARS => XC_TEMP := XC; YC_TEMP := (others=>'0' if K='1' then gamma := "01" ; CC_TEMP := not CC; else gamma := "00" ; CC_TEMP := CC; when others => 124
125 XC_TEMP := "11000"; YC_TEMP := (others=>'0' gamma := (others=>'0' CC_TEMP := (others=>'0' end case; R:=XC_TEMP+YC_TEMP+CC_TEMP+gamma; Rout<=R; if R=BERGERin then failure_out<='0'; else failure_out<='1'; end process prediction; BERGER_failure BERGERout <= failure_out; <= Rout; end BERGER_prediction_arch; Title : IOportC Design : xjobb Author : Andreas Soderberg Company : SP File : ioportc.vhd Version : 1.0 Date : Rev. by. : Description : Transparent IO-port, DDR is configured by IOportB The IO-port outputs forces to 0 when safe-state library IEEE; use IEEE.std_logic_1164.all; entity IOportc is port ( end IOportc; reset : in STD_LOGIC; conf_ddr : in STD_LOGIC; safe_pulse : in STD_LOGIC; safe_state : in STD_LOGIC; IOin : inout STD_LOGIC_VECTOR (11 downto 0 IOout : inout STD_LOGIC_VECTOR (11 downto 0) architecture IOportc_arch of IOportc is signal DDR : std_logic_vector(11 downto 0 signal ut_bus, in_bus : std_logic_vector(11 downto 0 process(in_bus, DDR, conf_ddr) if conf_ddr='1' then IOin<=(others =>'Z' else for i in 0 to 11 loop if DDR(i) = '1' then IOin(i) <= 'Z'; else IOin(i) <= in_bus(i 125
126 end loop; IOin(11 downto 4) <= (others =>'Z' IOin(3 downto 0) <=in_bus(3 downto 0 end process; process (IOin, IOout, DDR, conf_ddr, reset, safe_state, safe_pulse) if safe_state='1' or safe_pulse='1' then in_bus<=(others=>'0' ut_bus<=(others=>'0' DDR<=DDR; elsif reset='1' then DDR<=(others=>'0' ut_bus<=(others=>'0' in_bus<=(others=>'0' elsif conf_ddr='1' then DDR<=IOin; in_bus <= IOout; ut_bus <= IOin; else DDR<=DDR; for i in 0 to 11 loop if DDR(i) = '0' then in_bus <= IOout; else ut_bus <= IOin; end loop; end process; process(ut_bus, DDR) for i in 0 to 11 loop if DDR(i) = '0' then IOout(i) <= 'Z'; else IOout(i) <= ut_bus(i end loop; IOout(11 downto 4) <= ut_bus(11 downto 4 end process; end IOportc_arch; IOout(3 downto 0) <=(others => 'Z' Title : PULSE_COUNTER Design : xjobb Author : Andreas Soderberg Company : SP File : PULSE_COUNTER.vhd Version : 1.0 Date : Rev. by. : Description : State machine which monitors the pipe registers 126
127 library IEEE; use IEEE.std_logic_1164.all; entity PULSE_COUNTER is port ( reset pulse clk safe_state end PULSE_COUNTER; : in STD_LOGIC; : in STD_LOGIC; : in STD_LOGIC; : out STD_LOGIC architecture PULSE_COUNTE_arch of PULSE_COUNTER is signal clk_counter : integer range 0 to 8; signal clear_counter: std_logic; type state_type is(s1, s2, s3 signal state : state_type; process(clk,reset) if reset='1' then clk_counter <= 0; safe_state <= '0'; elsif clk'event and clk='1' then if clear_counter='1' then clk_counter<=0; else clk_counter <= clk_counter + 1; if clk_counter = 8 then safe_state <= '1'; end process; process(clk, reset) if reset='1' then state<=s1; clear_counter<='0'; elsif clk'event and clk='1' then case state is when s1 => clear_counter <= '0'; if pulse='1' then state<=s2; when s2=> clear_counter <= '0'; if pulse='0' then state<=s3; when s3=> clear_counter <= '1'; state<=s1; when others => state<=s1; clear_counter <= '0'; end case; end process; end PULSE_COUNTE_arch; 127
Datorteknik. Föreläsning 6. Processorns uppbyggnad, pipelining. Institutionen för elektro- och informationsteknologi, LTH. Mål
Datorteknik Föreläsning 6 Processorns uppbyggnad, pipelining Mål Att du ska känna till hur processorn byggs upp Att du ska kunna de viktigaste byggstenarna i processorn Att du ska känna till begreppet
Datorsystemteknik DVGA03 Föreläsning 8
Datorsystemteknik DVGA03 Föreläsning 8 Processorns uppbyggnad Pipelining Större delen av materialet framtaget av :Jan Eric Larsson, Mats Brorsson och Mirec Novak IT-inst LTH Innehåll Repetition av instruktionsformat
Digitala System: Datorteknik ERIK LARSSON
Digitala System: Datorteknik ERIK LARSSON Dator Primärminne Instruktioner och data Data/instruktioner Kontroll Central processing unit (CPU) Fetch instruction Execute instruction Programexekvering (1)
Digitalteknik EIT020. Lecture 15: Design av digitala kretsar
Digitalteknik EIT020 Lecture 15: Design av digitala kretsar November 3, 2014 Digitalteknikens kopplingar mot andra områden Mjukvara Hårdvara Datorteknik Kretskonstruktion Digitalteknik Elektronik Figure:,
Grundläggande datavetenskap, 4p
Grundläggande datavetenskap, 4p Kapitel 2 Datamanipulation, Processorns arbete Utgående från boken Computer Science av: J. Glenn Brookshear 2004-11-09 IT och Medier 1 Innehåll CPU ALU Kontrollenhet Register
F2: Motorola Arkitektur. Assembler vs. Maskinkod Exekvering av instruktioner i Instruktionsformat MOVE instruktionen
68000 Arkitektur F2: Motorola 68000 I/O signaler Processor arkitektur Programmeringsmodell Assembler vs. Maskinkod Exekvering av instruktioner i 68000 Instruktionsformat MOVE instruktionen Adresseringsmoder
LABORATION DATORTEKNIK D. Pipelining. Namn och personnummer. Version: (OS,OVA,AN)
LABORATION DATORTEKNIK D Pipelining Version: 1.4 2016 (OS,OVA,AN) Namn och personnummer Godkänd 1 blank sida 2 Innehåll 1 Inledning 5 1.1 Syfte................................. 5 1.2 Förberedelser............................
Datorsystem 2 CPU. Förra gången: Datorns historia Denna gång: Byggstenar i en dators arkitektur. Visning av Akka (för de som är intresserade)
Datorsystem 2 CPU Förra gången: Datorns historia Denna gång: Byggstenar i en dators arkitektur CPU Visning av Akka (för de som är intresserade) En dators arkitektur På en lägre nivå kan vi ha lite olika
Datormodell. Datorns uppgifter -Utföra program (instruktioner) Göra beräkningar på data Flytta data Interagera med omvärlden
Datormodell Datorns uppgifter -Utföra program (instruktioner) Göra beräkningar på data Flytta data Interagera med omvärlden Intel 4004 från 1971 Maximum clock speed is 740 khz Separate program and data
Hantering av hazards i pipelines
Datorarkitektur med operativsystem Hantering av hazards i pipelines Lisa Arvidsson IDA2 Inlämningsdatum: 2018-12-05 Abstract En processor som använder pipelining kan exekvera ett flertal instruktioner
Datorteknik. Tomas Nordström. Föreläsning 2. För utveckling av verksamhet, produkter och livskvalitet.
Datorteknik Tomas Nordström Föreläsning 2 För utveckling av verksamhet, produkter och livskvalitet. Föreläsning 2 Check av övningar Von Neumann arkitekturen Minne, CPU, I/O Instruktioner och instruktionscykeln
Övning1 Datorteknik, HH vt12 - Talsystem, logik, minne, instruktioner, assembler
Övning1 Datorteknik, HH vt12 - Talsystem, logik, minne, instruktioner, assembler Talsystem Talsystem - binära tal F1.1) 2 n stycken tal från 0 till 2 n 1 F1.2) 9 bitar (512 kombinationer) Talsystem - 2-
En Von Neumann-arkitektur ( Von Neumann-principen i föreläsning 1) innebär:
Lösningsförslag för 725G45-tentan 3/11-10 1. Vad menas med Von Neumann-arkitektur? (2p) En Von Neumann-arkitektur ( Von Neumann-principen i föreläsning 1) innebär: Data och instruktioner lagras i samma
Datorarkitekturer med operativsystem ERIK LARSSON
Datorarkitekturer med operativsystem ERIK LARSSON Dator Primärminne Instruktioner och data Data/instruktioner Kontroll Central processing unit (CPU) Fetch instruction Execute instruction Programexekvering
Minnet. Minne. Minns Man Minnet? Aktivera Kursens mål: LV3 Fo7. RAM-minnen: ROM PROM FLASH RWM. Primärminnen Sekundärminne Blockminne. Ext 15.
Aktivera Kursens mål: LV3 Fo7 Konstruera en dator mha grindar och programmera denna Aktivera Förra veckans mål: Konstruktruera olika kombinatoriska nät som ingår i en dator. Studera hur addition/subtraktion
Elektroteknik MF1016 föreläsning 9 MF1017 föreläsning 7 Mikrodatorteknik
Elektroteknik MF1016 föreläsning 9 MF1017 föreläsning 7 - Inbyggda system - Analog till digital signal - Utvecklingssystem, målsystem - Labutrustningen - Uppbyggnad av mikrokontroller - Masinkod, assemblerkod
Pipelining i Intel Pentium II
Pipelining i Intel Pentium II John Abdulnoor Lund Universitet 04/12/2017 Abstract För att en processor ska fungera måste alla komponenter inuti den samarbeta för att nå en acceptabel nivå av prestanda.
TSEA28 Datorteknik Y (och U)
Praktiska kommentarer TSEA8 Datorteknik Y (och U) Föreläsning Kent Palmkvist, ISY Dagens föreläsning RISC Mer information om hur arkitekturen fungerar Begränsningar Lab extra tillfälle för redovisning
TSEA28 Datorteknik Y (och U)
Praktiska kommentarer TSEA8 Datorteknik Y (och U) Föreläsning Kent Palmkvist, ISY Dagens föreläsning Latens/genomströmning Pipelining Laboration tips Sorteringsalgoritm använder A > B i flödesschemat Exemplet
Föreläsningsanteckningar till Konstruktionsmetoder 981027
Föreläsningsanteckningar till Konstruktionsmetoder 981027 Jämförelse mellan 68705P3 och 16F84 externt MC68705P3 PIC16F84 I/O 20 13 Kapsling 28-pin DIL 18-pin DIL Drivförmåga på pinnar PortB 10mA Sink,
Närliggande allokering Datorteknik
Närliggande allokering Datorteknik ERIK LARSSON TID Problem: Minnet blir fragmenterat Paging Demand paging Sida (S) Dela upp primärminnet i ramar (frames) och program i sidor (pages) Program 0 RD.0 1 RD.1
Datorarkitektur I. Tentamen Lördag 10 April Ekonomikum, B:154, klockan 09:00 14:00. Följande gäller: Skrivningstid: Fråga
Datorarkitektur I Tentamen Lördag 10 April 2010 Ekonomikum, B:154, klockan 09:00 14:00 Examinator: Karl Marklund 0704 73 32 17 [email protected] Tillåtna hjälpmedel: Penna Radergummi Linjal Följande
LV6 LV7. Aktivera Kursens mål:
Aktivera Kursens mål: LV6 LV7 Konstruera en dator mha grindar och programmera denna Aktivera Förra veckans mål: Konstruktruera olika kombinatoriska nät som ingår i en dator. Studera hur addition/subtraktion
SVAR TILL TENTAMEN I DATORSYSTEM, VT2013
Rahim Rahmani ([email protected]) Division of ACT Department of Computer and Systems Sciences Stockholm University SVAR TILL TENTAMEN I DATORSYSTEM, VT2013 Tentamensdatum: 2013-03-21 Tentamen består av totalt
Pipelining i Intel 80486
Lunds Universitet Pipelining i Intel 80486 EITF60 Datorarkitekturer med operativsystem Martin Wiezell 2017-12-04 Abstract This paper gives a brief description of the instruction pipeline of the Intel 80486
Tenta i Digitalteknik
Tenta i Digitalteknik Kurskod D0011E Tentamensdatum 2010-06-01 Skrivtid 9.00-14.00 (5 timmar) Maximalt resultat 50 poäng Godkänt resultat 25 poäng inkl bonus Jourhavande lärare Per Lindgren Tel 070 376
Tentamen den 12 januari 2017 Datorarkitektur med operativsystem, EDT621
Lunds Universitet LTH Tentamen den 12 januari 2017 Datorarkitektur med operativsystem, EDT621 Skrivtid: 8.00-13.00 Inga tillåtna hjälpmedel Uppgifterna i tentamen ger maximalt 60 poäng. Uppgifterna är
Lösningar till tentamen i EIT070 Datorteknik
Lösningar till tentamen i EIT070 Datorteknik Institutionen för Elektro- och informationsteknik, LTH Torsdagen den 13 mars 2014, klockan 14:00 19:00 i MA:10. Tillåtna hjälpmedel: på tentan utdelad formelsamling,
IBM POWER4, den första flerkärniga processorn och dess pipelines.
IBM POWER4, den första flerkärniga processorn och dess pipelines. 5 DECEMBER 2016 FÖRFATTARE: OSCAR STRANDMARK EXAMINATOR: ERIK LARSSON Abstract Rapporten redovisar IBM:s POWER-serie, generation ett till
Processor pipelining genom historien (Intel i9-intel i7)
Processor pipelining genom historien (Intel i9-intel i7) Besnik Redzepi Lunds Universitet Abstrakt/Sammanfattning Syftet med denna uppsats är att jämföra Intels nya generation processorer och deras pipelining.
Lunds Tekniska Högskola Datorarkitektur med operativsystem EITF60. Superscalar vs VLIW. Cornelia Kloth IDA2. Inlämningsdatum:
Lunds Tekniska Högskola Datorarkitektur med operativsystem EITF60 Superscalar vs VLIW Cornelia Kloth IDA2 Inlämningsdatum: 2018-12-05 Abstract Rapporten handlar om två tekniker inom multiple issue processorer
0.1. INTRODUKTION 1. 2. Instruktionens opcode decodas till en språknivå som är förstålig för ALUn.
0.1. INTRODUKTION 1 0.1 Introduktion Datorns klockfrekvens mäts i cykler per sekund, eller hertz. En miljon klockcykler är en megahertz, MHz. L1 cache (level 1) är den snabbaste formen av cache och sitter
Läs igenom hela laboration 5 innan du börjar beskriva instruktionsavkodaren i VHDL!
MCU LABORATION5 Laborationens syfte Läs igenom hela laboration 5 innan du börjar beskriva instruktionsavkodaren i VHDL! I denna laboration ska en enkel MCU (Micro-Controller_Unit) konstrueras. En MCU,
System S. Datorarkitektur - en inledning. Organisation av datorsystem: olika abstraktionsnivåer. den mest abstrakta synen på systemet
Datorarkitektur - en inledning Organisation av datorsystem: olika abstraktionsnivåer System S den mest abstrakta synen på systemet A B C Ett högnivåperspektiv på systemet a1 b1 c1 a2 b3 b2 c2 c3 En mera
Lösningar till tentamen i EIT070 Datorteknik
Lösningar till tentamen i EIT070 Datorteknik Institutionen för Elektro- och informationsteknik, LTH Onsdagen den 13 mars 2013, klockan 14:00 19:00 i Vic 2 A-D, 3 A-C. Tillåtna hjälpmedel: på tentan utdelad
Föreläsningsanteckningar 4. Pipelining
Föreläsningsanteckningar 4. Pipelining Olle Seger 2012, [email protected] 21 januari 2013 1 Inledning Denna föreläsning handlar om pipelining, som är den helt dominerande processorarkitekturen i dag. Man
Tentamen Datorteknik D del 2, TSEA49
Tentamen Datorteknik D del 2, TSEA49 Datum 2012-05-24 Lokal TER2 Tid 8-12 Kurskod TSEA49 Provkod TEN1 Kursnamn Datorteknik D del 2 Institution ISY Antal frågor 6 Antal sidor (inklusive denna 10 sida) Kursansvarig
Tentamen i Digitala system - EDI610 15hp varav denna tentamen 4,5hp
Tentamen i Digitala system - EDI610 15hp varav denna tentamen 4,5hp Institutionen för elektro- och informationsteknik Campus Helsingborg, LTH 2016-12-22 8.00-13.00 Uppgifterna i tentamen ger totalt 60
Datorsystem. Tentamen 2011-10-29
Datorsystem Tentamen 2011-10-29 Instruktioner Samtliga svar skall vara motiverade och läsbara. Eventuella tabeller och beräkningar som används för att nå svaret ska också finnas med i lösningen. Ett svar
Tentamen den 18 mars svar Datorteknik, EIT070
Lunds Universitet LTH Tentamen den 18 mars 2015 - svar Datorteknik, EIT070 Skrivtid: 14.00-19.00 Tillåtna hjälpmedel: Inga. Maximalt antal poäng: 50 poäng För betyg 3 krävs 20 poäng För betyg 4 krävs 30
HF0010. Introduktionskurs i datateknik 1,5 hp
HF0010 Introduktionskurs i datateknik 1,5 hp Välkommna - till KTH, Haninge, Datateknik, kursen och till första steget mot att bli programmerare! Er lärare och kursansvarig: Nicklas Brandefelt, [email protected]
4. Pipelining. 4. Pipelining
4. Pipelining 4. Pipelining Det finns en pipelinad biltvätt i Linköping spoltvätttork spoltvätt tork spolning tvätt tork De tre momenten tar lika lång tid Alla bilar går igenom samma program Väntetid 1/3
Digital- och datorteknik
Digital- och datorteknik Föreläsning #14 Biträdande professor Jan Jonsson Institutionen för data- och informationsteknik Chalmers tekniska högskola Vad vi har åstadkommit hittills: Med hjälp av kombinatoriska
Hannes Larsson - IDA 2, LTH Campus Helsingborg. NEC V R 4300i. Interlock-handling EDT621
Hannes Larsson - IDA 2, LTH Campus Helsingborg NEC V R 4300i Interlock-handling EDT621 Läsperiod 2, 2017 Innehållsförteckning s.2 - Förord s.2 - Inledning s.2 - NEC VR-4305 s.3 - Pipeline s.4 - Interlocks
ALU:n ska anslutas hur då?
Aktivera Kursens mål: LV3 Fo7 Konstruera en dator mha grindar och programmera denna Aktivera Förra veckans mål: Konstruktruera olika kombinatoriska nät som ingår i en dator. Studera hur addition/subtraktion
Programexempel för FLEX
Aktivera Kursens mål: Konstruera en dator mha grindar och programmera denna Aktivera Förra veckans mål: Konstruera styrenheten. genom att. implementera olika maskininstruktioner i styrenheten. Kunna använda
Digitala System: Datorteknik ERIK LARSSON
Digitala System: Datorteknik ERIK LARSSON Huvudled (H) Trafikljus för övergångsställe Trafikljus för huvudled (H) Trafikljus: Sväng vänster (H->T) Gående - vänta Trafikljus för tvärgata (T) Tvärgata (T)
Moment 2 Digital elektronik. Föreläsning Inbyggda system, introduktion
Moment 2 Digital elektronik Föreläsning Inbyggda system, introduktion Jan Thim 1 Inbyggda system, introduktion Innehåll: Historia Introduktion Arkitekturer Mikrokontrollerns delar 2 1 Varför lär vi oss
Digital- och datorteknik, , Per Larsson-Edefors Sida 1
Digitala it elektroniksystem t Professor Per Larsson-Edefors [email protected] Digital- och datorteknik, 101122, Per Larsson-Edefors Sida 1 Introduktion Konstruktionsalternativ Kretskort med diskreta standardkomponenter.
Digitalteknik och Datorarkitektur 5hp
Foto: Rona Proudfoot (some rights reserved) Vi skall nu kolla närmare på hur det går till när en instruktion utförs. Fetch = + Digitalteknik och Datorarkitektur hp path & Control maj 2 [email protected]
Läsminne Read Only Memory ROM
Läsminne Read Only Memory ROM Ett läsminne har addressingångar och datautgångar Med m addresslinjer kan man accessa 2 m olika minnesadresser På varje address finns det ett dataord på n bitar Oftast har
Tenta i Digitalteknik
Tenta i Digitalteknik Kurskod D0011E Tentamensdatum 2011-08-26 Skrivtid 9.00-14.00 Maximalt resultat 50 poäng Godkänt resultat 25 poäng Jourhavande lärare Per Lindgren Tel 070 376 8150 Tillåtna hjälpmedel
Svar till tentamen den 16 december 2013 Datorarkitekturer med operativsystem, EDT621, 7,5 poäng
Lunds Universitet LTH Ingenjörshögskolan, Helsingborg Svar till tentamen den 16 december 2013 Datorarkitekturer med operativsystem, EDT621, 7,5 poäng Skrivtid: 08.00-13.00 Tillåtna hjälpmedel: Inga. Maximalt
Ett minneselements egenskaper. F10: Minneselement. Latch. SR-latch. Innehåll:
F: Minneselement Innehåll: - Latchar - Flip-Flops - egister - Läs- och skrivminne (andom-access Memory AM) - Läsminne (ead Only Memory OM) Ett minneselements egenskaper Generellt sett så kan följande operationer
Laboration nr 3 behandlar
(2013-04-20) Laboration nr 3 behandlar Konstruktion och test av instruktioner (styrsignalsekvenser) för FLISP Följande uppgifter ur Arbetsbok för DigiFlisp ska vara utförda som förberedelse för laborationen.
Tentamen. TSEA22 Digitalteknik 5 juni, 2015, kl
Tentamen TSEA22 Digitalteknik 5 juni, 2015, kl. 08.00-12.00 Tillåtna hjälpmedel: Inga. Ansvarig lärare: Mattias Krysander Visning av skrivningen sker mellan 10.00-10.30 den 22 juni på Datorteknik. Totalt
Tentamen. Datorteknik Y, TSEA28
Tentamen Datorteknik Y, TSEA28 Datum 2017-10-26 Lokal TER1, TER3 Tid 8-12 Kurskod TSEA28 Provkod TEN1 Kursnamn Provnamn Datorteknik Y Skriftlig tentamen Institution ISY Antal frågor 6 Antal sidor (inklusive
Digitalteknik och Datorarkitektur
Digitalteknik och Datorarkitektur Tentamen Tisdag 12 Januari 2010 Pollacksbackens skrivsal, klockan 08:00 13:00 Examinator: Karl Marklund 018 471 10 49 0704 73 32 17 [email protected] Tillåtna hjälpmedel:
Spekulativ exekvering i CPU pipelining
Spekulativ exekvering i CPU pipelining Max Faxälv Datum: 2018-12-05 1 Abstrakt Speculative execution is an optimisation technique used by modern-day CPU's to guess which path a computer code will take,
Datorteknik. Föreläsning 2. Programmering i C och assembler MIPS instruktionsarkitektur. Institutionen för elektro- och informationsteknologi, LTH
Datorteknik Föreläsning 2 Programmering i C och assembler MIPS instruktionsarkitektur Mål Att ge en inblick i programspråket C Att veta varför assemblerprogrammering är viktigt Att börja arbeta med MIPS-assembler
Datorarkitekturer med operativsystem ERIK LARSSON
Datorarkitekturer med operativsystem ERIK LARSSON Översikt Processorn Maskininstruktioner Dator Primärminne Data/instruktioner Kontroll Central processing unit (CPU) Fetch instruction Execute instruction
Digital Aritmetik Unsigned Integers Signed Integers"
Digital Aritmetik Unsigned Integers Signed Integers" Slides! Per Lindgren! EISLAB! [email protected]! Original Slides! Ingo Sander! KTH/ICT/ES! [email protected]! Talrepresentationer" Ett tal kan representeras
Datorarkitekturer med operativsystem ERIK LARSSON
Datorarkitekturer med operativsystem ERIK LARSSON Semantic gap Alltmer avancerade programmeringsspråk tas fram för att göra programvaruutveckling mer kraftfull Dessa programmeringsspråk (Ada, C++, Java)
Föreläsningsanteckningar 5. Cacheminnen
Föreläsningsanteckningar 5. Cacheminnen Olle Seger 2012 Anders Nilsson 2016 1 Inledning Bakgrunden till att cacheminnen behövs för nästan alla datorer är enkel. Vi kan kallt räkna med att processorn är
KALKYLATOR LABORATION4. Laborationens syfte
LABORATION4 KALKYLATOR Laborationens syfte I denna laboration ska en enkel kalkylator konstrueras med hjälp av VHDL och utvecklingsverktyget Vivado från Xilinx. Hårdvaran realiseras på det redan bekanta
Övning1 Datorteknik, HH vt12 - Talsystem, logik, minne, instruktioner, assembler
Övning1 Datorteknik, HH vt12 - Talsystem, logik, minne, instruktioner, assembler Talsystem Talsystem - binära tal F1.1. Hur många unsigned integers kan man göra med n bitar? Vilket talområde får dessa
Mål. Datorteknik. Innehåll. Vad händer med en add-instruktion? Vad händer med en add-instruktion. Instruktioner som bitmönster i minnet
Mål Datorteknik Föreläsning 2 Att ge en inblick i programspråket C Att veta varför assemblerprogrammering är viktigt Att börja arbeta med MIPS-assembler Att känna till något om programmeringstekniker Att
Digital- och datorteknik
Digital- och datorteknik Föreläsning #17 Biträdande professor Jan Jonsson Institutionen för data- och informationsteknik Chalmers tekniska högskola Tallriksmodellen Stackoperationer Element kan endast
Ext-13 (Ver ) Exempel på RTN-beskrivning av FLEX-instruktioner
Ext-3 (Ver 203-04-2) Exempel på RTN-beskrivning av FLEX-instruktioner. Figur på sidan 2 i detta häfte visar hur datorn FLEX är uppbyggd. På sidan visas dessutom hur ALU:ns funktion väljs med styrsignalerna
TENTAMEN Datorteknik (DO2005) D1/E1/Mek1/Ö1
Halmstad University School of Information Science, Computer and Electrical Engineering Tomas Nordström, CC-lab TENTAMEN Datorteknik (DO2005) D1/E1/Mek1/Ö1 Datum: 2012-05- 23 Tid och plats: 9:00 13:00 i
Det finns en hemsida. Adressen är http://www.idt.mdh.se/kurser/ct3760/
CT3760 Mikrodatorteknik Föreläsning 1 Torsdag 2005-08-25 Upprop. Det finns en hemsida. Adressen är http://www.idt.mdh.se/kurser/ct3760/ Kurslitteratur är Per Foyer Mikroprocessorteknik. Finns på bokhandeln.
Konstruera en dator mha grindar och programmera denna Använda en modern microcontroller
Aktivera Kursens mål: LV5 Fo12 Konstruera en dator mha grindar och programmera denna Använda en modern microcontroller Aktivera Förra veckans mål: Konstruera styrenheten. genom att. implementera olika
Digital- och datorteknik
Digital- och datorteknik Föreläsning #8 Biträdande professor Jan Jonsson Institutionen för data- och informationsteknik Chalmers tekniska högskola Aritmetik i digitala system Grindnät för addition: Vi
Föreläsningsanteckningar 3. Mikroprogrammering II
Föreläsningsanteckningar 3. Mikroprogrammering II Olle Seger 2012 Anders Nilsson 2016 1 Inledning Datorn, som vi byggde i förra föreläsningen, har en stor brist. Den saknar I/O. I denna föreläsning kompletterar
Uppgift 1: a) u= a c + a bc+ ab d +b cd
Uppgift 1: a) u= a c a bc ab d b cd b) a b c d u 0 0 0 0 1 0 0 0 1 1 0 0 1 0 1 0 0 1 1 0 0 1 0 0 1 0 1 0 1 1 0 1 1 0 1 0 1 1 1 1 1 0 0 0 1 1 0 0 1 0 1 0 1 0 1 1 0 1 1 0 1 1 0 0 0 1 1 0 1 0 1 1 1 0 0 1
Dataminne I/O Stack 0x005D 0x3D SP low byte 0x005E 0x3E SP high byte
CT3760 Mikrodatorteknik Föreläsning 4 Tisdag 2005-09-06 Stacken I datasammmanhang är en stack ett minnesområde. Det är processorn som använder stacken. För att skapa en stack anger man en adress i stackpekarregistret.
CE_O3. Nios II. Inför lab nios2time
IS1200 Exempelsamling till övning CE_O3, 2015 CE_O3. Nios II. Inför lab nios2time 3.1. Logiska operationer (se uppgift 1.2 c) Repetera (eller lär dig) innebörden av de logiska operationerna "bitvis AND",
Ext-13 (Ver ) Exempel på RTN-beskrivning av FLEX-instruktioner
Ext-3 (Ver 204-04-08) Exempel på RTN-beskrivning av FLEX-instruktioner. Figur på sidan 2 i detta häfte visar hur datorn FLEX är uppbyggd. På sidan visas dessutom hur ALU:ns funktion väljs med styrsignalerna
Ansvarig lärare: Olof Andersson, Telefon 021-101314 (besöker skrivsalen)
MÄLRLENS HÖGSKOL Institutionen för elektroteknik Tentamen Mikrodatorteknik T3760 atum 2005-10-28 Tid 08.30 12.30 nsvarig lärare: Olof ndersson, Telefon 021-101314 (besöker skrivsalen) Om du klarat samtliga
Lösningar till tentamen i EIT070 Datorteknik
Lösningar till tentamen i EIT070 Datorteknik Institutionen för Elektro- och informationsteknik, LTH Onsdagen den 7 mars 2012, klockan 14:00 19:00 i Vic 2, 3. Tillåtna hjälpmedel: på tentan utdelad formelsamling,
Tentamen. Datorteknik Y, TSEA28
Tentamen Datorteknik Y, TSEA28 Datum 2017-08-15 Lokal TER4 Tid 14-18 Kurskod Provkod Kursnamn Provnamn Institution Antal frågor 6 Antal sidor (inklusive denna sida) 6 Kursansvarig Lärare som besöker skrivsalen
Digital- och datorteknik
Digital- och datorteknik Föreläsning #19 Biträdande professor Jan Jonsson Institutionen för data- och informationsteknik Chalmers tekniska högskola Normaltillstånd vs undantagstillstånd I normaltillstånd
Design av digitala kretsar
Föreläsningsanteckningar Föreläsning 15 - Digitalteknik Design av digitala kretsar Efter att ha studerat fundamentala digitaltekniska områden, ska vi nu studera aspekter som gränsar till andra områden.
TSEA28 Datorteknik Y (och U)
TSEA28 Datorteknik Y (och U) Föreläsning 9 Kent Palmkvist, ISY TSEA28 Datorteknik Y (och U), föreläsning 9, Kent Palmkvist 2017-03-20 2 Dagens föreläsning Byggblocken i en processor Hur de fungerar Grundläggande
