IfuComplex.mcJune 18, 1981 9:49 AM%1TITLE[IfuComplex];IM[ILC,0];TOP LEVEL;* November 6, 1978 3:39 PM%ifu.cmassemble and place entire ifu diagnosticifuSave.cmassemble ifuSaveDefs, ifuDefs, ifuPostambleifuOnly.cmassemble ifu.mcifu1.cmassemble ifu1.mcifuPlace.cmplace ifu diagnosticifuSaveDefs.cmassemble IfuSaveDefs (d1Lang, kernelAlu, preamble)ifuDefs.cmassemble IfuDefsifuPostamble.cmassemble Ifu's version of PostambleifuToLogin.cmdump all ifu sources onto [ivy]dorado>IfuSources.dm,dump ifu.midas, ifu.mb onto [ivy]dorado>ifu.dmifuToIvy.cmdumps sources and .mb, as above except it goes to official dorado directoriesifuFiles.cmlist of all the source files associated with ifu%%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++June 18, 1981 9:49 AMChange this file to IfuComplexMay 20, 1981 3:25 PMAccommodate split of ifu3.mc into ifu3a, ifu3b, ifu3cFebruary 1, 1980 6:26 PMChange preBegin into restartDiagnostic -- postamble had already defined that label.February 1, 1980 11:53 AMAdd preBegin code to zero memoryOK.October 14, 1979 3:33 PMRemove beginIfu4 -- now a separate diagnostic.September 27, 1979 10:00 AMAdd call to beginIfu4.September 19, 1979 11:16 PMAdd beginIfuTests label.September 17, 1979 5:16 PMcall beginIfu1,3 rather than goto them.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++restartDiagnostic:memoryOK_a0;BEGIN:t _ (r0)+1;* init the stkp to onestkp _ t;RBASE _ rbase[defaultRegion];MEMBX_0s;rscr _ A0;call[setBR], rscr2 _ A0;call[resetIfu];* remove this 3 line hack asapbeginIfuTests:call[beginIfu3a];call[beginIfu3b];call[beginIfu3c];r1 _ (r0)+1;goto[done];* CODE for midas debuggingtop level;top level;l1: branch[l1];l2:call[justReturn];branch[l2];l3:call[justReturn];call[justReturn];branch[l3];l4:call[justReturn];call[justReturn];`gp *< N bAq a _ ^ ]K \p q( Zp  q+ Yp  q XUp q Wp  q Tp  q2 S_p  q R"p q# Pp  qE O? Nip  qrq' Kp  q0 J IsL H6@F E@D}5 C@@BS @@?# >J@= . ;@: 9T@8 6@5' 4^L 0pq1/h .*pq1, 1+1*r1)41' 1&1%| #p 1!q1 1H1 1 R1 1 pq pq11 pq111 pq11 yD VB%]5IfuComplex.mcJune 18, 1981 9:49 AM%2call[justReturn];branch[l4];l5:call[justReturn];call[justReturn];call[justReturn];call[justReturn];branch[l5];l6:call[justReturn];call[justReturn];call[justReturn];call[justReturn];call[justReturn];branch[l6];l7:call[justReturn];call[justReturn];call[justReturn];call[justReturn];call[justReturn];call[justReturn];branch[l7];END;`gp *< N1bAq1a _9pq11]1\1[1ZC Xxpq11W;1U1T1S1RE Pzpq11O=1M1L1K1JG1I Fn Fkk!lIfuSimple.mcJune 18, 1981 9:48 AM%1TITLE[IfuSimple];IM[ILC,0];TOP LEVEL;* November 6, 1978 3:39 PM%ifu.cmassemble and place entire ifu diagnosticifuSave.cmassemble ifuSaveDefs, ifuDefs, ifuPostambleifuOnly.cmassemble ifu.mcifu1.cmassemble ifu1.mcifuPlace.cmplace ifu diagnosticifuSaveDefs.cmassemble IfuSaveDefs (d1Lang, kernelAlu, preamble)ifuDefs.cmassemble IfuDefsifuPostamble.cmassemble Ifu's version of PostambleifuToLogin.cmdump all ifu sources onto [ivy]dorado>IfuSources.dm,dump ifu.midas, ifu.mb onto [ivy]dorado>ifu.dmifuToIvy.cmdumps sources and .mb, as above except it goes to official dorado directoriesifuFiles.cmlist of all the source files associated with ifu%%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++June 18, 1981 9:48 AMChange this file to ifuSimpleMay 20, 1981 3:25 PMAccommodate split of ifu3.mc into ifu3a, ifu3b, ifu3cFebruary 1, 1980 6:26 PMChange preBegin into restartDiagnostic -- postamble had already defined that label.February 1, 1980 11:53 AMAdd preBegin code to zero memoryOK.October 14, 1979 3:33 PMRemove beginIfu4 -- now a separate diagnostic.September 27, 1979 10:00 AMAdd call to beginIfu4.September 19, 1979 11:16 PMAdd beginIfuTests label.September 17, 1979 5:16 PMcall beginIfu1,3 rather than goto them.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++restartDiagnostic:memoryOK_a0;BEGIN:t _ (r0)+1;* init the stkp to onestkp _ t;RBASE _ rbase[defaultRegion];MEMBX_0s;rscr _ A0;call[setBR], rscr2 _ A0;call[resetIfu];* remove this 3 line hack asapbeginIfuTests:call[beginIfu1];r1 _ (r0)+1;goto[done];* CODE for midas debuggingtop level;top level;l1: branch[l1];l2:call[justReturn];branch[l2];l3:call[justReturn];call[justReturn];branch[l3];l4:call[justReturn];call[justReturn];call[justReturn];branch[l4];gp *d;N bAq a _ ^ ]K \p q( Zp  q+ Yp  q XUp q Wp  q Tp  q2 S_p  q R"p q# Pp  qE O? Nip  qrq' Kp  q0 J IsL H6@F E@D}5 C@@BS @@?# >J@= . ;@: 9T@8 6@5' 4^L 0pq1/h .*pq1, 1+1*r1)41' 1&1%| #p 1!q1 1H 1 1 Jpq pq11B wpq11:1 2pq11 1 1 y : VB%]5IfuSimple.mcJune 18, 1981 9:48 AM%2l5:call[justReturn];call[justReturn];call[justReturn];call[justReturn];branch[l5];l6:call[justReturn];call[justReturn];call[justReturn];call[justReturn];call[justReturn];branch[l6];l7:call[justReturn];call[justReturn];call[justReturn];call[justReturn];call[justReturn];call[justReturn];branch[l7];END;gp *d;N bAq11a1_1^1]K [pq11ZC1Y1W1V1UM Spq11RE1Q1O1N1MO1L IR IsdIfu1.mcJune 18, 1981 9:26 AM%1 TITLE[Ifu1];%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++CONTENTSTESTDESCRIPTIONbeginIfu1:Control subroutine that calls each test in this filei.XXXXXXIfuReset, PcFG_, getPcX, ifuJump, resched, various scope loops, etc.ifuMemRW:read and write ifu memoryiMemRandAddrs:Ifu memory r/w test that uses random addrs and random data.iMemAddrs:Test addressing logic for ifu memory.ifuMScopeLoop:infinite loop that reads location 0 then location 1 of IfuMiSingleStepTest:single step, under Dorado processor control, ifuitTestCase1:First test that uses the ifuTest register%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%June 18, 1981 9:26 AMMove common code from this file into IfuSubrs.mcMay 18, 1981 2:25 PMFix nextPat to invoke cycleRandV to get better performance from the random number generator.February 1, 1980 7:58 PMFix stack handling bug in return code of addressing test. Fix old bug in fastStore code that wasfetching rather than storing.February 1, 1980 7:48 PMAdd code to mask out unwanted bits from getIfuLH in addressing test.February 1, 1980 6:37 PMAdd iMemAddrs, an addressing logic test.February 1, 1980 5:06 PMImprove the set of patterns generated by pat16.September 19, 1979 1:13 PMReset expectedDispatch<0 after invoking iSingleStepTest.September 19, 1979 12:55 PMMove beginIfu1 to the beginning of the file, add more and better comments, and set upiSingleStepTest to loop 400 times.September 17, 1979 5:29 PMAdd iSingleStepTest.July 3, 1979 1:53 AMIncrement return link in checkException by 1 -- because afterdispatch will also decrement it & weneed compatability. This increment occurs after the potential error check where the link has beendecremented to make error interpretation easier.July 3, 1979 1:17 AMDecrement return link in checkException by 1 -- so that it points to where we came from ratherthan where to return to, which is irrelevant..July 3, 1979 12:06 AMAdd code to enable dynamically selected exception conditions.June 29, 1979 11:46 AMModify afterDispatch to save POINTERS into (stack+1), but to return control with stkp = enteringvalue. Do this since afterDispatch resets RBASE to defaultRegion, and some tests want to check thevalue that RBASE got set to when the IfuJump occured.June 20, 1979 9:14 AMAdd call to resetIfu in iMemRandAddrs and cause beginIfu1 to invoke iMemRandAddrs.June 20, 1979 8:50 AMAdd ifuLHmaskC masking to data in iMemRandAddrsJune 20, 1979 7:35 AMAdd random address generation test (iMemRandAddrs)June 19, 1979 10:34 AMFix register clobbering bug in new version of ifuMemRW.June 18, 1979 8:56 AMFix bug in 3rd pattern of nextPat16.June 17, 1979 4:04 PMAdd entry points for all the exception conditionsJune 15, 1979 3:24 PMEnable random patterns in iMemRWJune 5, 1979 12:43 PMRemove i.testCase2L since test2 has been removed from default diagnostic.June 5, 1979 11:31 AMAdd disableConditionTaskMay 30, 1979 10:08 AMAdd random numbers to pat16 code; diddle iMemRW to reset the Ifu only once.May 9, 1979 9:05 AMFix subroutine mode error in ifuMScopeLoop. Move contents section to top of file & add more!dgp(:N bAq aB_ ]K Zp  q4 Yp qD XUp q Wp  q; Up  qr q Tp  q; S_p q0 R"p  q) PB Ni M,1K0 J1Is\ H61Fa E D}1C@D B1@( ?1>J/ = 1;8 :19TU 8" 615 4^13 a 1b 00 /h1.*^ ,. +1*r= )41'` &c %|5 $>1#R !1 / H1 3 17 R1$ 11 \1 1I f1) 1 K p1 3\ X DR]7Ifu1.mcJune 18, 1981 9:26 AM%2comments.May 4, 1979 10:57 AMAdd scope loop for checking Ram speed.May 3, 1979 8:44 AMAdd calls to setIUsingInstrSet before invoking initIfuM1Thru(3,16)April 26, 1979 9:53 AMAdd pat8 subroutines.April 25, 1979 12:13 PMAdd fastExit, fastFetch, fastStore code.April 24, 1979 5:27 PMRemove references to dispatchOffset, simplify afterDispatch.April 22, 1979 5:10 PMMove iAddFGParity thru itStep into ifuStepSubrs.mcFebruary 7, 1979 10:35 AMAdd breakpoints to rampe, kfault, resched entries; explicitly place all the entry points for theinstructions.February 6, 1979 2:16 PMAdd requisite noop after PcF_.February 5, 1979 12:54 PMAdd ifAd20 -- ifu pause/halt codeFebruary 5, 1979 9:59 AMChange opifad13,14,16 to do ifuJumps directly.January 18, 1979 6:44 PMFix misc. bugs in pattern16, muffler bit reading codeJanuary 17, 1979 3:52 PMMore Rev-Bb mods: define exception code for instrSet 1 (locations 200,204,214,234,274). DefineitMosFhSh.January 15, 1979 4:52 PMRev-Bb mods: instrSet bits, complemented, are or'd into Exception addresses. InstrSet bits 2,3pick bytes right to left. Cycled 0 pattern for Ifu memory test.%!dgp(:N bAq a1_& ^1]KB \1Z Y1XU( W1U< T1S_2 R"1P` O Ni1M, K1J! Is1H6. F1E5 D}1C@_ B @1?_ >J@ =  ;C,_Ifu1.mcJune 18, 1981 9:26 AM%3* February 1, 1980 6:37 PMbeginIfu1:pushReturn[];call[disableConditionalTask];call[ifuMemRW];call[iMemRandAddrs];call[iMemAddrs];call[iSingleStepTest];expectedDispatch_a1;returnP[];!dgp(:N bAq ap 1_q 1^1]K1\1Z1Y1XU1W Tzc<Ifu1.mcJune 18, 1981 9:26 AM%4* November 30, 1978 9:07 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++SINGLE STEP and INITIAL DEBUGGING CODE:%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++top level;i.getPcX: branch[.], t _ not(PcX');i.ifuJump: ifuJump[0];* try ifu next macro...i.ifuJumpF:ifuJump[0, r odd], r0;* conditional branch condition is falsenoop;i.ifuJumpT:t _ (r0)+1;ifuJump[0, ALU=0];* conditional branch condition is truenoop;i.mos: branch[.], mos _ t;* set instructyion set w/ ti.nextData: branch[.], t _ ID;* get next data from ifui.noResched: branch[.], noReschedule;* NO reschedi.reset: branch[.], IfuReset;* Ifu Reseti.resched: branch[.], reschedule;* reschedi.setPcFG: branch[.], PcF_t;* SET Ti.test: branch[.], ifuTest _ t;* load TEST registeri.tick: branch[.], ifutick;* Ticki.WriteLHL: * Write LEFT HALF IFU ram SET. rscr3 = addr, rscr4 = valuerscr _ rscr4;* value to write kept in rscr4call[putIfuLH], t _ rscr3;* address to write kept in rscr3branch[i.WriteLHL];* do it again for scope loopi.WriteRHL: * Write RIGHT HALF IFU ram. SET rscr3 = addr, rscr4 = valuerscr _ rscr4;* value to write kept in rscr4call[putIfuRH], t _ rscr3;* address to write kept in rscr3branch[i.WriteRHL];* do it again for scope loopi.ReadLHL: * Read LEFT HALF IFU ram. SET rscr3 = addrcall[getIfuLH], t _ rscr3;* keep addr to read in rscr3branch[i.ReadLHL];* do it again for scope loopi.ReadRHL: * Read RIGHT HALF IFU ram. SET rscr3 = addrcall[getIfuRH], t _ rscr3;* keep addr to read in rscr3branch[i.ReadRHL];* do it again for scope loopi.testCase1L:call[setIUsingInstrSet], t _ 1C;call[InitIfuM1Thru3];call[itTestCase1];branch[.-1];%* commented out since we're removed test2 from ifu default diagnostici.testCase2L:call[setIUsingInstrSet], t _ 1C;call[initIfuM0Thru16];call[itTestCase2];branch[.-1];%i.WRl:*Write, then Read an ifu memory locationrscr _ 1c;* use FF constants so it's easy to patch.t _ 2c;call[putIfuRH];t_1c;call[getIfuRH];branch[i.WRl];!dgp(:N bAq aB _' ^B Zf Y)pq Vp q + T3p Rq+'Q Op Niq M,+&K Ispq+ Fp q+ D}p q+ Bpq+ ?p q+ = p q+ :pq+ 8pq+ 5p qrq"4^ +3 +1+ 0p qrq/h +.*+,+ *rp qrq)4+'+ &p qrq%|+$>+ "-p  qt7 E p ~qA  p+q(f +))   p 3  ;u]/Ifu1.mcJune 18, 1981 9:26 AM%5i.RWl:*Read, then Write an ifu memory locationt_1c;* use FF constants so it's easy to patch.call[getIfuRH];rscr _ 1c;t _ 2c;call[putIfuRH];branch[i.RWl];!dgp(:N a+q(_+)^]K \ZY V;u6Ifu1.mcJune 18, 1981 9:26 AM%6* May 4, 1979 10:59 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iMemRWRead and write the ifu RAMFOR pat IN NPats DOsaveRandState[];-- remember random number stateFOR iAddrX IN [0..1777B] DOifuLoMem[addr] _ getPattern[pat, addr];ifuHiMem[addr] _ getPattern[pat, addr];ENDLOOP:restoreRandState[];-- restore random number stateFOR iAddrX IN [0..1777B] DOIF ifuLoMem[addr] # getPattern[pat,addr] THEN ERROR;IF ifuHiMem[addr] # getPattern[pat,addr] THEN ERROR;ENDLOOP;-- end of address loop;ENDLOOP;-- end of pattern loopNotice that this code pushes the stack and keeps the current address there.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuMemRW: * read and write the Ifu memorypushReturn[];IfuReset[];* make sure its stoppedcall[iPat16], stkp+1;* init 16 bit patterns. keep addr on stackiMemPatL:call[nextPat16];* select next 16 bit pattern or exitbranch[afterIMemPatL,ALU=0];noop;* for placementcall[saveRandState];call[iIAddr];* init ifu addressesiMemAddrWL:call[nextIAddr];* select next ifu address or exitbranch[afterIAddrWL,ALU=0], stack _ t;* save current addr on stack!noop;* Write Left Half of Ifu memorycall[getPat16], t _ stack;* rtn t = patternrscr _ t;* pass pattern in rscrcall[putIfuLH], t _ stack;* write ifu left half* Write Right Half of Ifu memorycall[getPat16], t _ stack;* rtn t = patternrscr _ t;* pass pattern in rscrcall[putIfuRH], t _ stack;* write Ifu right halfbranch[iMemAddrWL];!dgp(:N bAq aB^p+q ][+ZfXU'W'US+RPz4O=4M+K+ IK HB F$pq+@D @C +@Bl+r A.p@?q+$@>@=v+@:@9 + 8p @7Bq+!@6&+rq@4 2L@1+@/+@.+ ,@*+@)+@(`+@'# %J +q#@= +&@:+ 9Tp @8q 6p @5q +( 4;<3Ifu1.mcJune 18, 1981 9:26 AM%8* June 20, 1979 9:13 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iMemRandAddrsThis test generates a series of pairs ofrandom addresses, writes into those pairs of locations andthen checks the data to see that it is correct.FOR itrs IN [0..10000] DOaddr2 _ addr1 _ getRandom[] and (1777B);UNTIL addr2 # addr1 DO addr2 _ getRandom[] and (1777B);lh1 _ getRandom[] and lhMask; rh1 _ getRandom[];lh2 _ getRandom[] and lhMask; rh2 _ getRandom[];ifuLhMem[addr1] _ lh1; ifuRhMem[addr1] _ rh1;ifuLhMem[addr2] _ lh2; ifuRhMem[addr2] _ rh2;IF (ifuLhMem[addr1] and ifuLHmask) # lh1 THEN ERROR;IF ifuRhMem[addr1] # rh1 THEN ERROR:IF (ifuLhMem[addr2] and ifuLHmask) # lh2 THEN ERROR;IF ifuRhMem[addr2] # rh2 THEN ERROR;ENDLOOP;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iMemRandAddrs: pushReturn[];call[resetIfu];t _ 10000C;cnt _ t;* loop 10000B timesiMemRandAddrsL:noop;* for placementcall[get1Rand];iAddr1 _ t _ t and (1777C);iAddr2 _ t;iMemRandAddrsL2:* get 2 unique, random addressescall[get1Rand];t _ t and (1777C);* isolate the bits for ifu ram addressest # (iAddr1);branch[iMemRandAddrsL2, ALU=0];* still need different, random addressnoop;* for placementcall[get1Rand], iAddr2 _ t;* get random valuescall[get1Rand], value1left _ t and (IfuLHmaskC);call[get1Rand], value1right _ t;call[get1Rand], value2left _ t and (IfuLHmaskC);* now write random data into our two randomly chosen locationsvalue2right _ t;* write into iAddr1rscr _ value1left;call[putIfuLh], t _ iAddr1;rscr _ value1right;call[putIfuRh], t _ iAddr1;rscr _ value2left;* write into iAddr2call[putIfuLh], t _ iAddr2;rscr _ value2right;call[putIfuRh], t _ iAddr2;* now check that the data is correct.call[getIfuLh], t _ iAddr1;t _ t and (IfuLHmaskC);* remove the extra, non Ifu Ram bitst # (value1left);skpif[ALU=0];iMemRandAddrsErr1lh:* value at iAddr1 has left half value in Terror;* and it doesn't match value1left.call[getIfuRh], t _ iAddr1;t # (value1right);skpif[ALU=0];iMemRandAddrsErr1rh:* value at iAddr1 has right half value in Terror;* and it doesn't match value1rightcall[getIfuLh], t _ iAddr2;t _ t and (IfuLHmaskC);* remove the extra, non Ifu Ram bits!dgp(:N bAq aB)_p ^qb ]K/ [:Y)(W7V0Up0T3-R-Q4Pz$O=4M$L KB JGp q @I @G @F+ Dp@Bq+@A@@[@? =p+q@<@;e+(@:' @8+&@7+@51+@30@2@1y0 .>@,+@+E@*@(@'@%+@#@"@!Y %@c@&+$@@ mp+q*@0+"@@w@: p+q+@+"@ D@ +$ B](Ifu1.mcJune 18, 1981 9:26 AM%9t # (value2left);skpif[ALU=0];iMemRandAddrsErr2lh:* value at iAddr2 has left half value in Terror;* and it doesn't match value2leftcall[getIfuRh], t _ iAddr2;t # (value2right);skpif[ALU=0];iMemRandAddrsErr2rh:* value at iAddr2 has right half value in Terror;* and it doesn't match value2rightloopUntil[cnt=0&-1, iMemRandAddrsL];returnP[];!dgp(:N@bAq@a _p+q*@^+!@\@Z@Y XUp+q+@W+"@T$@R" r O<KIfu1.mcJune 18, 1981 9:26 AM%10* February 1, 1980 6:39 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iMemAddrsThis test checks the memory addressing logic. It assumes that the data bits work. Failures inthe data bits may produce a spurious complaint from this test. The algorithm is identical to the oneemployed in all the microcoded addressing tests for the memory system.Storage Addressing TestBackground memory w/ 0 then write -1 into ascending addresses. Before the write,check that the word that is about to be written is still zero. Suppose it is non zero.Then there was an addressing error. Remember the address of the non zero word, background memory withzeros again and proceed writing -1s. This time, check thepreviously clobbered address each time before writing the -1. This approach will catch the referencethat clobbers the known location. The same algorithm can be applied fordescending addresses, mutatis mutandi, to finish a complete check of the addressing logic.iAddrCheck: PROCEDURE=BEGINzeroMem: PROCEDUREBEGINFOR i IN IfuMemLimits DO IfuMem[i]_0; ENDLOOP;END;findErrUp: PROCEDURE [clobbered: VA] =BEGINzeroMem[];FOR i IN VA DOIF IfuMem[clobbered]#0 THEN SIGNAL ErrUp[i-1, clobbered];IfuMem[i] _ -1;ENDLOOP;SIGNAL IntermittentErrUp[clobbered];END;findErrDown: PROCEDURE [clobbered: VA] =BEGINzeroMem[];FOR i DECREASING IN VA DOIF IfuMem[clobbered] #0 THEN SIGNAL ErrDown[i+1, clobbered];IfuMem[i] _ -1;ENDLOOP;SIGNAL IntermittentErrDown[clobbered];END;-- this is the programzeroMem[];FOR i IN VA DOIF IfuMem[i] # 0 THEN FindErrUp[i];IfuMem[i] _ -1;ENDLOOP;zeroMem[];FOR i DECREASING IN VA DOIF IfuMem[i] # 0 THEN FindErrDown[i];IfuMem[i] _ -1;ENDLOOP;END;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iMemAddrs:pushReturn[];call[zeroIfuMemory];call[iIAddr],stkp+1;iAddrUpL:call[nextIAddr];branch[iAddrUpLxit, alu=0], stack _ t;noop;call[getIfuLH],t_stack;* check the left halfPD_t and (IfuLHmaskC);skpif[ALU=0];branch[iAddrUpFindErr];rscr_a1;call[putIfuLH],t_stack;* write all ones into left halfcall[getIfuRH],t_stack;* check the right halfPD_t;!dgp(:N bAq aB _p@^q_ ]Ke \F&\Zp XUqP WV Ue T9 S_d R"G PZ Nip q M,Kpq JIs.H6Fp qED} C@ B9@?>J$= ;p q:9T 86<54^3 &10/h .* ,#+*r)4 '&%%|$># !B p 1Hq 1 1 Rp1q1&1111 1f1)1 1 p1 3B D]Ifu1.mcJune 18, 1981 9:26 AM%11skpif[ALU=0];branch[iAddrUpFindErr];rscr_a1;call[putIfuRH],t_stack;* write all ones into right halfbranch[iAddrUpL];iAddrUpLxit:call[zeroIfuMemory];call[iIAddrDownCtrl];iAddrDownL:call[nextIAddrDown];branch[iAddrTestDone, alu=0], stack _ t;noop;call[getIfuLH],t_stack;* check the left halfPD_t and (IfuLHmaskC);skpif[ALU=0];branch[iAddrDownFindErr];rscr_a1;call[putIfuLH],t_stack;* write all ones into left halfcall[getIfuRH],t_stack;* check the right halfPD_t;skpif[ALU=0];branch[iAddrDownFindErr];rscr_a1;call[putIfuRH],t_stack;* write all ones into right halfbranch[iAddrDownL];!dgp(:N1bAq 1a1_1^1\ Yp 1XUq1W Tp 1S_q1R"(1P1Ni1M,1K 1J1Is1H61E1D}1C@ 1B1@1?1= f :n)W-|Ifu1.mcJune 18, 1981 9:26 AM%12* January 11, 1979 9:14 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iAddrUpFindErrThis test tries to isolate the reference that clobbered the location (denote it the target location)that was detected by the iAddrUpL loop. The test proceeds as before except that as it ascends memoryit continually checks to see if the target location has been clobbered yet.In general, stack[stkp] contains the "current" address, andstack[stkp-1] contains the clobbered address detected in iAddrUpL.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iAddrUpFindErr:t_stack&+1;* we'll save clobbered (target location)stack_t;* location in stack!call[zeroIfuMemory];stkp-1;call[getIfuLH],t_stack&+1;* reexamine target locationPD_t and (IfuLHmaskC);skpif[ALU=0],stkp-1;iAddrUpErr1a:* zeroIfuMemory didn't work. stkp haserror;* address in question.call[getIfuRH], t_stack&+1;PD_t;skpif[alu=0],stkp-1;iAddrUpErr1b:* zeroIfuMemory didn't work. stkp haserror;* address in question.call[iIAddr],stkp+1;iAddrUpFindL:call[nextIAddr];branch[iAddrUpNoFind, alu=0], stack&-1 _ t;noop;call[getIfuLH],t_stack&+1;* check the left half of target addrPD_t and (IfuLHmaskC);skpif[ALU=0];iAddrUpErr2a:* the last store, (value on the stack)-1,error;* clobbered location at (stkp-1).rscr_a1;call[putIfuLH],t_stack;* write all ones into left halfstkp-1;* must check right half of targert addrcall[getIfuRH],t_stack&+1;* check the right halfPD_t;skpif[ALU=0];iAddrUpErr2b:* the last store, (value on the stack)-1,error;* clobbered location at (stkp-1).rscr_a1;call[putIfuRH],t_stack;* write all ones into right halfbranch[iAddrUpFindL];iAddrUpNoFind:error;* intermittent error;!dgp(:N bAq aB)b_p ^qTrq ]KpqD \$rq Y; XUB WB TpS_q +rqR"+PONi+M,K Jp +q%Is+FED} C@p +q%B+? >Jp = q;+:8+$65 4^p +q)3 +!10+.*+',++*r )4p +q)'+!&%|+# p qH+ DJ#Ifu1.mcJune 18, 1981 9:26 AM%13* February 1, 1980 7:57 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iAddrDownFindErrThis test tries to isolate the reference that clobbered the location (denote it the target location)that was detected by the iAddrDownL loop. The test proceeds as before except that as it descendsmemory it continually checks to see if the target location has been clobbered yet. Use Flush_ toforce the target munch out of the cache.In general, stack[stkp] contains the "current" address, andstack[stkp-1] contains the clobbered address detected in iAddrUpL.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iAddrDownFindErr:t_stack&+1;* we'll save clobbered (target location)stack_t;* location in stack!call[zeroIfuMemory];stkp-1;call[getIfuLH],t_stack&+1;* reexamine target locationPD_t and (IfuLHmaskC);skpif[ALU=0],stkp-1;iAddrDownErr1a:* zeroIfuMemory didn't work. stkp haserror;* address in question.call[getIfuRH], t_stack&+1;PD_t;skpif[alu=0],stkp-1;iAddrDownErr1b:* zeroIfuMemory didn't work. stkp haserror;* address in question.call[iIAddrDownCtrl],stkp+1;iAddrDownFindL:call[nextIAddrDown];branch[iAddrDownNoFind, alu=0], stack _ t;noop;call[getIfuLH],t_stack&+1;* check the left half of target addrPD_t and (IfuLHmaskC);skpif[ALU=0];iAddrDownErr2a:* the last store, (value on the stack)-1,error;* clobbered location at (stkp-1).rscr_a1;call[putIfuLH],t_stack;* write all ones into left halfstkp-1;* must check right half of targert addrcall[getIfuRH],t_stack&+1;* check the right halfPD_t;skpif[ALU=0];iAddrDownErr2b:* the last store, (value on the stack)-1,error;* clobbered location at (stkp-1).rscr_a1;call[putIfuRH],t_stack;* write all ones into right halfbranch[iAddrDownFindL];iAddrDownNoFind:error;* intermittent error;iAddrTestDone:pReturnP[];!dgp(:N bAq aB(_p ^qTrq ]Kp q> \+rq' Z( XU; WB UB S_p@R"q +rq@P+@O@Ni@M,+@K@J Isp+q%@H6+@E@D}@C@ Bp+q%@@+@=  ;p@:q@9T*@8@5+$@4^@3 1p+q)@0+!@/h@.*+@++'@*r+@)4@' &p+q)@%|+!@$>@#+ ! Hp@ q+ p @Rq  COIfu1.mcJune 18, 1981 9:26 AM%14* February 1, 1980 7:25 PMzeroIfuMemory:pushReturn[];call[iIAddr],stkp+1;* we'll keep the addr on stackziMemL:call[nextIAddr];branch[ziMemXit, ALU=0], stack_t;* exit if no more addresses to zerorscr_a0;call[putIfuLH], t_stack;* zero the left halfrscr_a0;call[putIfuRH], t_stack;* zero the right halfbranch[ziMemL];ziMemXit:pReturnP[]; returnP[];!dgp(:N bAq ap @_q @^+ \p@Zq@Y!+#@XU@W+@U@T+@S_ Pp@Oq Ni | K7m@YIfu1.mcJune 18, 1981 9:26 AM%15* May 4, 1979 11:06 AMtop level;IfuMScopeLoop:t _ 1c;stkp _ t;call[resetIfu];rscr _ 0c;t _ 0c;call[putIfuLH];* write zeros in location 0 left halfrscr _ 0c;t _ 0c;call[putIfuRH];* write zeros in location 0 right halfrscr _ cm1;t _ 1c;call[putIfuLH];* write all ones in location 1 left halfrscr _ cm1;t _ 1c;call[putIfuRH];* write all ones in location 1 right halfifuMScopeL:t _ 0c;call[getIfuLH];* read location zerot _ 0c;call[getIfuRH];t _ 1c;call[getIfuLH];* read location onet _ 1c;call[getIfuRH];branch[ifuMScopeL];!dgp(:N bAq@a _p @^q@]K@\@Y @XU@W+%@U @T@S_+&@P @O@Ni+(@M, @K@J+) H6p q@F@E+@D}@C@@B@@+@?@>J@= * ;;u,_Ifu1.mcJune 18, 1981 9:26 AM%16* September 17, 1979 6:06 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iSingleStepTestThis test uses the Ifu's TEST register to single step the ifu througits paces. The program invokes subroatines that actually clock the Ifu and selected FFs to occur.The "microcode" that we are singlestepping would look like,PcF_2;* try a 2-byte instructionIfuJump[0];t_ID;* somehow, we get back here after IfuJumpt # 10c;* we expect 10 for alphaskpif[ALU=0];IDerr:error;t_not(pcX');t # (2c);skpif[ALU=0];* we set PcF to 2PcXerr1:error;t_ID;t # (2c);* we should get IL after alphaskpif[ALU=0];IDerr2:error;PcF_3c;IfuJump[0];* somehow, we get back here after IfuJumpt_ID;t # 20C;skpif[ALU=0];* expect 20=alpha, 100=betaIDerr3:error;t_not(PcX');t # (3c);* we set PcF to 3skpif[ALU=0];PcXerr2:error;t_ID;t # (100c);* expect 100=betaskpif[ALU=0];IdErr4:error;t_ID;t # (3c);* should get IL after betaskpif[ALU=0];IDerr5:error;note that the microcode above is a GROSS OVERSIMPLIFICATION of what is happening. It provides"orientation" only!The way this test works is to initialize the Ifu ram and then to loop 400B times calling thesubroutine that actually tests, in single-step mode, the Ifu.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iSingleStepTest:* single step, under Dorado processor control, ifupushReturn[];call[setIusingInstrSet], t_1c;call[initIfuM1Thru3];t_400c, stkp+1;stack_t;iSingleStepTestL:noop;call[itTestCase1];* work happens herestack_(stack)-1;loopUntil[ALU<0, iSingleStepTestL];pReturnP[];!dgp(:N bAq aB) _p ^qD ]Kc \;ZY XU)WU T S_R" PO  Ni M,KJIs H6 FD}C@ )B@?  >J = ; :9T 8 64^3 1 0 /h.*,+ *r )4 '^ & $>\ #= !B p+q2@H @ @@@R pq@@+@\@#@ " C/ZCIfu1.mcJune 18, 1981 9:26 AM%17* November 24, 1978 3:07 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ run the ifu thru one test case%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++itTestCase1: subroutine;pushReturn[];itTestCase10:call[itResetSH];* RESETt _ 1c;* use instruction set 1call[itMosFhSh];%OPCODE 1 in this sequence comes from location 2 in the Ifu Ram. It is a two byter. We must step the"2" into J. The ifudata is 10 for this sequence. We write PcF with 2.%call[itNoopFHSH];call[itNewPcFHSH], t _ 2c;* NewPc_call[itNoopFHSH], t _ 2c;* keep new pc value on Bmux during tickcall[itNoopFH];noop;* here for placementitTestCase11:call[itMemAckSHFH];* MemAck Sh Fhcall[itMakeFDSH];* MakeF_D SHcall[itNoopFH];call[itSetFGSH], t _ 2c;* value for Jcall[itSetFGFH], t _ 10c;* value for HitTestCase12:call[itNoopSH];call[itNoopFH];expectedDispatch _ opAt15;* we expect ifujump to goto 10call[itIfuJumpSH];* IfuJump[0]call[itNoopFH];call[itNextDataSH];* _NextDatat#(10C);skpif[ALU=0];itCaseErr10:Breakpoint;noop;* here for placementcall[itNoopFH];call[itGetPcXSH];* _PcXt # (2c);skpif[ALU=0];itCaseErr12:Breakpoint;* pcx wasn't correctt_1c;* patch this instruction if you wantQ_t;* to loop more than onceitCaseL1:noop;* Get Instr Length from _NextDatacall[itNoopFH];call[itNextDataSH];* _NextDatat#(2c);* should get instruction lengthskpif[ALU=0];itCaseErr13:Breakpoint;noop;t_(Q)-1;loopUntil[ALU=0, itCaseL1],Q_t;* check out instruction length a few times!dgp(:N bAq aB _ ^B \wp q [: Yp Xq+pWq+VD U Sc RF QNPN+pMq+'LXK+ Ip Hq+p Gbq+p F$qD+ C+ Blp A.q?>+=v+p <8q:+p9q8 7Bp 6q 4+32L+p1q/ .p -Vq +*+$)+ (`p'#q+p%q$+p#jq+"- p q t7+* C/Mr Ifu1.mcJune 18, 1981 9:26 AM%18* January 17, 1979 4:12 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++OPCODE2 in this sequence comes from location 3 in the Ifu Ram. It is a three byter. We must step the"3" into J. Likewise we step 20 and 100 into H. Allow the normal sequencing of the pipe to incrementPcFG, etc.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++call[itNoopFH];call[itMemAckShFh];* MemAck Sh Fhcall[itMakeFDAckSh];* MakeF_D, memAck Shcall[itMemAckFH];* MemAck, Fhcall[itSetFGFDSh], t _ 3c;* address word 3 in ifu ram (data for j)call[itSetFGFh], t _ 20c;* data for hitTestCase21:call[itNoopSH];call[itSetFGFH], t _ 100c;*Third bytenoop;* for placementexpectedDispatch _ opAt15;* we expect ifujump to goto 10call[itIfuJumpSH];* IfuJump[0]call[itNoopFH];call[itNextDataSH];* _NextDatat#(20C);skpif[ALU=0];itCaseErr20:Breakpoint;noop;* here for placementcall[itNoopFH];call[itGetPcXSH];* _PcX for 3 byte opcodet # (4c);skpif[ALU=0];itCaseErr22:Breakpoint;* pcx wasn't correctcall[itNoopFH];call[itNextDataSH];* _NextData for 3rd bytet # (100c);skpif[ALU=0];itCaseErr23:Breakpoint;t_1c;* patch this instruction if you wantQ_t;* to loop more than onceitCaseL2:noop;* top of _NextData loop that gets "IL"call[itNoopFH];* when it does next datascall[itNextDataSH];t#(3c);* should get instruction lengthskpif[ALU=0];itCaseErr24:Breakpoint;noop;* for placementt_(Q)-1;loopUntil[ALU=0, itCaseL2],Q_t;* check out instruction length a few timesitTestCase1Xit:returnP[];!dgp(:N bAq aB _d ^e ]K \BTZTYjp TXUqpTWqjp TUq p TTq p S_ TR"qTP p TOqTM, TKjp TJqTH6jpTFqTE D}p TC@q TBT?T>JjpqT= T; :p T9Tq .T6T5jpq T4^ T3 1p qT0 T.*$T, +pT*rqpqT)4T'T&T%| $>p T#q T!T TH%* pTq  /DMIfu2.mcApril 22, 1979 5:24 PM%1* INSERT[D1ALU.MC];* TITLE[Ifu2];* INSERT[PREAMBLE.MC];%May 28, 1981 2:56 PMChange Bmux to BmuxRM to keep midas happy.April 22, 1979 5:24 PMMove initIfuM0thru16 to ifuRamSubrsApril 19, 1979 10:28 AMCall resetIfu before using endIfuWd macro.January 17, 1979 4:50 PMUse instruction set 1, init IfuM field by field.%%CONTENTSTESTDESCRIPTIONitTestCase2Long sequence of opcodes%!gp(`:rN bAq a _ ^ ]K1\* Z1Y# XU1W* U1T0 S_ P'O M,' I  H F"" ]Ifu2.mcApril 22, 1979 5:24 PM%2* November 30, 1978 9:27 AM%itTestCase2:This is a long sequence of opcodes that we step thru the ifu by using the test register.ExpectedDispatch remains valid across ifuJumps. ExpectedDispatch<0 ==> don't check where the dispatchcame from.%itTestCase2: subroutine;saveReturn[iLink0];t _ 1c;call[itMosFhSh];* use instruction set 1itCase2Clk0:t _ (r0)-1;clockCount _ t;iTick[test.fh];* 0iReset[test.sh];* 1iTick[test.fh];* 2iTick[test.sh];* 3iNewPc[test.fh];* 4;iNewPc[test.sh];* 5BmuxRM _ 40c;iTick[test.fh];* 6iTick[test.ShAck];* 7noop;itCase2Clk10:iTick[test.FhAck];* 10iTick[test.ShAckFd];* 11iTick[test.FhAck];* 12iTick[test.ShAckFd, 1];* 13iTick[test.FhAck, 1];* 14iTick[test.ShFd];* 15iTick[test.fh, 2];* 16iTick[test.sh];* 17noop;itCase2Clk20:iTick[test.Fh];* 20expectedDispatch _ opAt15;Ijump[test.Sh];* 21iTick[test.fh, 21];* 22iJumpData[test.ShAck, 2];* 23iTick[test.FhAck, 22];* 24iJumpData[test.ShAckFd, 2];* 25iTick[test.FhAck, 2];* 26iJumpData[test.ShAckFd, 3];* 27itCase2Clk30:noop;iTick[test.FhAck, 23];* 30iJumpData[test.ShFd];* 31iTick[test.Fh, 24];* 32iJump[test.Sh, 3];* 33iTick[test.Fh, 25];* 34Idata[test.ShAck];* 35iTick[test.FhAck, 26];* 36iJumpData[test.ShAckFd, 25];* 37noop;itCase2Clk40:iTick[test.FhAck, 25];* 40iData[test.ShAckFd, 1];* 41iTick[test.FhAck, 2];* 42iJumpData[test.ShFd];* 43iTick[test.Fh, 27];* 44iJump[test.Sh, 2];* 45iTick[test.Fh, 30];* 46iJumpData[test.ShAck, 3];* 47noop;itCase2Clk50:iTick[test.FhAck, 30];* 50!gp(`:rN bAq a_p q ]X [e Zf W Tp q R"PO+ Nip M,q KJ+Is+H6+F+E+D}+C@ B+@+? >Jp = q+;+:+9T+8+6+5+4^+3  1p 0q+/h.*+,+++*r+)4+'+&+ %|p $>q#+!+ +H+ +++R+ p q+\++++f+)+ +  pp  3q+ D]aIfu2.mcApril 22, 1979 5:24 PM%3iJumpData[test.ShAckFd, 30];* 51iTick[test.FhAck, 30];* 52iJumpData[test.ShAckFd, 31];* 53iTick[test.FhAck, 31];* 54expectedDispatch _ cm1;* turn off dispatch address checkingiJump[test.ShFd];* 55iTick[test.Fh, 32];* 56iJump[test.Sh, 3];* 57noop;itCase2Clk60:iTick[test.Fh, 33];* 60iData[test.ShAck];* 61iTick[test.FhAck, 34];* 62iJumpData[test.ShFd, 1];* 63iTick[test.Fh, 34];* 64iData[test.ShAck, 3];* 65iTick[test.FhAck, 35];* 66iJumpData[test.ShAckFd];* 67noop;itCase2Clk70:iTick[test.FhAck];* 70iJumpData[test.ShFd];* 71iTick[test.Fh, 36];* 72iJump[test.Sh, 2];* 73iTick[test.Fh, 37];* 74iData[test.ShAck, 1];* 75iTick[test.FhAck, 37];* 76iJumpData[test.ShAckFd, 37];* 77noop;itCase2Clk100:iTick[test.FhAck, 37];* 100iJumpData[test.ShAckFd, 1];* 101iTick[test.FhAck, 3];* 102iJumpData[test.ShFd];* 103iTick[test.Fh, 40];* 104iJump[test.Sh];* 105iTick[test.Fh, 41];* 106iJumpData[test.ShAck, 2];* 107noop;itCase2Clk110:iTick[test.FhAck, 42];* 110iData[test.ShAckFd, 2];* 111iTick[test.FhAck, 2];* 112iJumpData[test.ShAckFd, 1];* 113iTick[test.FhAck, 10];* 114iJumpData[test.ShFd];* 115iTick[test.Fh, 3];* 116iJump[test.Sh, 13];* 117noop;itCase2Clk120:iTick[test.Fh, 13];* 120iJumpData[test.ShAck, 7];* 121iTick[test.FhAck, 7];* 122iJumpData[test.ShAckFd, 7];* 123iTick[test.FhAck, 7];* 124iJump[test.ShAckFd, 7];* 125iTick[test.FhAck, 377];* 126iJump[test.ShFd, 1];* 127noop;itCase2Clk130:iTick[test.Fh, 1];* 130iJump[test.ShAck];* 131iTick[test.FhAck];* 132ijumpData[test.ShAckFd];* 133iTick[test.FhAck];* 134iJump[test.ShAckFd, 13];* 135iTick[test.FhAck, 3];* 136iJump[test.ShAckFd, 7];* 137noop;itCase2Clk140:iTick[test.FhAck, 7];* 140iJump[test.ShAckFd, 1];* 141!gp(`:rNbAq+a+_+^+]K+r"\q+Z+Y+XU Wp Uq+T+S_+R"+P+O+Ni+M,+K Jp Isq+H6+F+E+D}+C@+B+@+? >Jp = q+;+:+9T+8+6+5+4^+3  1p 0q+/h+.*+,+++*r+)4+'+& %|p $>q+#+!+ +H+ +++R p q++\++++f+)+  p  pq+ 3+ 8]Ifu2.mcApril 22, 1979 5:24 PM%4iTick[test.FhAck, 1];* 142iJumpData[test.ShAckFd, 3];* 143iTick[test.FhAck, 3];* 144iJump[test.ShAckFd, 1];* 145iTick[test.FhAck, 7];* 146iJump[test.ShFd];* 147noop;itCase2Clk150:iTick[test.Fh, 3];* 150iJump[test.Sh];* 151iTick[test.Fh];* 152iJumpData[test.ShAck, 10];* 153iTick[test.FhAck, 10];* 154iJumpData[test.ShAckFd, 10];* 155iTick[test.FhAck, 10];* 156iJump[test.ShAckFd, 10];* 157noop;itCase2Clk160:iTick[test.FhAck, 3];* 160iJump[test.ShFd];* 161iTick[test.Fh];* 162iJump[test.ShAck];* 163iTick[test.FhAck];* 164iJumpData[test.ShAckFd];* 165iTick[test.FhAck];* 166iJump[test.ShAckFd, 1];* 167noop;itCase2Clk170:iTick[test.FhAck];* 170iJump[test.ShAckFd, 12];* 171iTick[test.FhAck];* 172iJump[test.ShFd];* 173iTick[test.Fh];* 174iJumpData[test.ShAck];* 175iTick[test.FhAck, 12];* 176iJumpData[test.ShAckFd, 12];* 177noop;itCase2Clk200:iTick[test.FhAck, 12];* 200iJump[test.ShAckFd, 11];* 201iTick[test.FhAck, 12];* 202iJump[test.ShFd];* 203iTick[test.Fh];* 204iJump[test.ShAck];* 205iTick[test.FhAck, 43];* 206iJumpData[test.ShAckFd, 43];* 207noop;itCase2Clk210:iTick[test.FhAck, 43];* 210iJump[test.ShAckFd, 12];* 211iTick[test.FhAck, 11];* 212iJump[test.ShAckFd, 12];* 213iTick[test.FhAck, 12];* 214iJump[test.ShAckFd, 43];* 215iTick[test.FhAck, 43];* 216iJumpData[test.ShAckFd, 10];* 217noop;itCase2Clk220:iTick[test.FhAck, 10];* 220iJump[test.ShAckFd, 14];* 221iTick[test.FhAck, 12];* 222iJump[test.ShAckFd, 3];* 223iTick[test.FhAck, 3];* 224iJump[test.ShAckFd, 44];* 225iTick[test.FhAck, 44];* 226iJumpData[test.ShAckFd, 5];* 227noop;itCase2Clk230:iTick[test.FhAck, 5];* 230iJump[test.ShAckFd, 12];* 231iTick[test.FhAck, 14];* 232!gp(`:rNbAq+a+_+^+]K+\+Z Yp XUq+W+U+T+S_+R"+P+O+Ni M,p Kq+J+Is+H6+F+E+D}+C@+B @p ?q+>J+= +;+:+9T+8+6+5 4^p 3 q+1+/h+.*+,+++*r+)4+' &p %|q+$>+#+!+ +H+ ++ Rp q+++\++++f+) p  q+ p+ 3+ #E]Ifu2.mcApril 22, 1979 5:24 PM%5iJump[test.ShFd];* 233iTick[test.Fh];* 234iJump[test.ShAck];* 235iTick[test.FhAck, 44];* 236iJumpData[test.ShAckFd, 44];* 237noop;itCase2Clk240:iTick[test.FhAck, 44];* 240iJump[test.ShAckFd, 3];* 241iTick[test.FhAck, 43];* 242iJump[test.ShFd];* 243iTick[test.Fh, 44];* 244iJump[test.Sh, 10];* 245iTick[test.Fh, 5];* 246iData[test.ShAck, 1];* 247noop;itCase2Clk250:iTick[test.FhAck, 1];* 250iJumpData[test.ShAckFd, 5];* 251iTick[test.FhAck, 5];* 252iJumpData[test.ShAckFd, 10];* 253iTick[test.FhAck, 10];* 254iJump[test.ShAckFd, 2];* 255iTick[test.FhAck, 45];* 256iJump[test.ShFd, 7];* 257noop;itCase2Clk260:iTick[test.Fh, 373];* 260iJump[test.ShAck];* 261iTick[test.FhAck];* 262iJumpData[test.ShAckFd];* 263iTick[test.FhAck];* 264iJumpData[test.ShAckFd];* 265iTick[test.FhAck];* 266iJump[test.ShAckFd, 1];* 267noop;itCase2Clk270:iTick[test.FhAck, 5];* 270iJump[test.ShAckFd, 10];* 271iTick[test.FhAck, 12];* 272iJump[test.ShFd, 2];* 273iTick[test.Fh, 2];* 274iJumpData[test.ShAck, 7];* 275iTick[test.FhAck, 7];* 276iJumpData[test.ShAckFd, 7];* 277noop;itCase2Clk300:iTick[test.FhAck, 7];*300iJump[test.ShAckFd, 4];*301iTick[test.FhAck, 4];*302iJump[test.ShFd];*303iTick[test.Fh, 5];*304iJump[test.Sh];*305iTick[test.Fh, 46];*306iJumpData[test.ShAck, 5];*307noop;itCase2Clk310:iTick[test.FhAck, 47];*310iJumpData[test.ShAckFd, 5];*311iTick[test.FhAck,5];*312iData[test.ShAckFd,6];*313iTick[test.FhAck,50];*314iJumpData[test.ShFd];*315iTick[test.Fh,51];*316iData[test.Sh,6];*317noop;itCase2Clk320:iTick[test.Fh,6];*320iJumpData[test.Sh,6];*321iTick[test.Fh,52];*322iData[test.ShAck];*323!gp(`:rNbAq+a+_+^+]K+\ Zp Yq+XU+W+U+T+S_+R"+P+O Nip M,q+K+J+Is+H6+F+E+D}+C@ Bp @q+?+>J+= +;+:+9T+8+6 5p 4^q+3 +1+0+/h+.*+,+++*r )4p 'q+&+%|+$>+#+!+ +H+  p q+R+++\++++f )p  q+ + p+ 3+R #E]Ifu2.mcApril 22, 1979 5:24 PM%6iTick[test.FhAck];*324iData[test.ShFd];*325iTick[test.Fh,53];*326iJumpData[test.ShAck,4];*327noop;itCase2Clk330:iTick[test.FhAck,5];*330iData[test.ShAckFd];*331iTick[test.FhAck];*332iData[test.ShFd];*333iTick[test.Fh,54];*334iJumpData[test.Sh,5];*335iTick[test.Fh,55];*336iJumpData[test.ShAck,6];*337noop;itCase2Clk340:iTick[test.FhAck,55];*340iData[test.ShAckFd,55];*341iTick[test.FhAck,55];*342iJumpData[test.ShFd,56];*343iTick[test.Fh,56];*344iData[test.ShAck];*345iTick[test.FhAck,57];*346iJumpData[test.ShFd,6];*347noop;itCase2Clk350:iTick[test.Fh,60];*350iData[test.ShAck];*351iTick[test.FhAck];*352iData[test.ShFd];*353iTick[test.Fh,61];*354iJumpData[test.Sh,4];*355iTick[test.Fh,6];*356iData[test.ShAck];*357noop;itCase2Clk360:iTick[test.FhAck];*360iData[test.ShFd];*361iTick[test.Fh,62];*362iJumpData[test.ShAck];*363iTick[test.FhAck,63];*364iJumpData[test.ShFd,5];*365iTick[test.Fh,63];*366iData[test.ShAck,64];*367noop;itCase2Clk370:iTick[test.FhAck,64];*370iData[test.ShFd,4];*371iTick[test.Fh,64];*372iJumpData[test.ShAck,4];*373iTick[test.FhAck,6];*374iData[test.ShAckFd];*375iTick[test.FhAck];*376iJumpData[test.ShFd];*377noop;itCase2Clk400:iTick[test.Fh,65];*400iJumpData[test.Sh];*401iTick[test.Fh,66];*402iJumpData[test.ShAck,5];*403iTick[test.FhAck,67];*404iData[test.ShAckFd,5];*405iTick[test.FhAck,5];*406iData[test.ShFd,4];*407noop;itCase2Clk410:iTick[test.Fh,15];*410iJumpData[test.ShAck];*411iTick[test.FhAck,1];*412iData[test.ShFd];*413iTick[test.Fh];*414iJumpData[test.Sh];*415!gp(`:rNbAq+a+_+^+]K \p Zq+Y+XU+W+U+T+S_+R"+P Op Niq+M,+K+J+Is+H6+F+E+D} C@p Bq+@+?+>J+= +;+:+9T+8 6p 5q+4^+3 +1+0+/h+.*+,++ *rp )4q+'+&+%|+$>+#+!+ +H  p q++R++++\++ p fq+)+ + + p+ 3+ "]Ifu2.mcApril 22, 1979 5:24 PM%7iTick[test.Fh,4];*416iJumpData[test.ShAck];*417noop;itCase2Clk420:iTick[test.FhAck,1];*420iTick[test.ShFd];*421iTick[test.Fh];*422iTick[test.Sh];*423iTick[test.Fh];*424iTick[test.Sh];*425iTick[test.Fh];*426iJump[test.Sh];*427noop;itCase2Clk430:iTick[test.Fh,4];*430iJumpData[test.ShAck];*431returnUsing[iLink0];!gp(`:rNbAq+a+_ ^p ]Kq+\+Z+Y+XU+W+U+T+S_ R"p Pq+O+NiX NF"nIfu3a.mcMay 20, 1981 3:10 PM%1%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Table of ContentsOrganized by Occurence of subroutine in this ListingSubroutineFunction+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++beginIfu3a:"main control", it calls the test subroutinesifuPcAlphaPipe:Check the data bits of the Pc pipe and the Alpha pipeifuXqtTest:execution test for Ifu%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%May 20, 1981 3:10 PMConstruct this file out of ifu3.mcMay 19, 1981 4:50 PMBegin adding iMiscEffects test (for RestoreStkP, IDFetch_, Fetch_ID, etc.)February 1, 1980 8:05 PMFix miscellaneous comments, fix performance bug in iFastTest.September 19, 1979 1:14 PMSet expectedDispatch<0 in beginIfu3 -- for robustness.September 18, 1979 11:07 AMCause tests that enableConditionalHold to disableConditionalTask as well -- seem to havemysterious bug that is associated with tasking. Fix some comments in IfuXqtTest.September 17, 1979 6:32 PMFix beginIfu3 so that it is a subroutine that calls the test implemented here.August 1, 1979 6:16 PMFix bug in ifuBrkInsTest -- failing to load BrkIns from left half of Bmux.August 1, 1979 3:24 PMInvert order of BrkIns_, Pcf_.August 1, 1979 11:11 AMRearrange parts of IfuBrkInsTest for easier scope looping.August 1, 1979 10:45 AMAdd noop to ifuBrkInsTest to accommodate placement problems.August 1, 1979 10:36 AMFix omitted initialization of ifu memory in ifuBrkInsTest, missking skip instr, set instrset inifu.August 1, 1979 9:28 AMAdd the ifuBrkInsTest, add misc. comments.July 3, 1979 2:27 AMfix stack underflow error in resched test.July 3, 1979 2:21 AMFix bug in iReschedTest -- clobbered the value that we load PcF with.July 3, 1979 2:08 AMAdd noops for placement purposes. -- apparently setIUsingInstrSet causes some problems.July 3, 1979 1:55 AMFix resched test, further, to handle the fact that reschedules don't occur after one IfuJump butafter several.July 3, 1979 12:37 AMCause iRamPEtest to enable the ramPE exception condition.June 29, 1979 5:02 PMFix ifuChaos' ID checking to preserve ID in a register rather than xoring it with the expectedvalue.June 29, 1979 11:54 AMCause ifuChaos to reset memBase and memBX inside the ifuChaosL; check ;Rbase immediately after theIfuJump (in ifuChaos), since afterDispatch leaves POINTERS in a very fragile place (stk+1).June 29, 1979 10:53 AMAdd missing "coreturn" at sicR2 (inside setIfuChaosRet).June 24, 1979 6:40 PMChange ifuChaos to use getIfuMBase, getIfuRBase for checking.June 19, 1979 9:53 AMFix stack bug in iRamtest.June 18, 1979 9:24 AMFix functional bugs in iRamPEtest (check for resched loc, reset rbase, membase, callsetUsingInsrSet.June 18, 1979 9:01 AMFix stack bugs in iRamPEtest.June 17, 1979 4:30 PMAdd iRamPEtest.June 6, 1979 10:30 AMChaos placement errors.June 5, 1979 11:40 AMAdd calls to enableConditionalTaskJune 1, 1979 6:16 PM!dgp)b:N bAqB(`ap_4^q "  ]K?\p " q-Zp" q5Yp " q XUB U T1S_" R"1PJ O1Ni= M,1K6 J1IsX H6Q F1EN D}1C@J B1@ ?1>J: = 1;< :19T_ 8 615* 4^13 * 110E /h1.*W ,1+` *r )41'9 &1%|^ $> #1!b [ H1 8 1= R1 1T \ 1 1f )1  1 p" 3 ~ D],Ifu3a.mcMay 20, 1981 3:10 PM%2Fix ifuChaos errors.May 30, 1979 10:16 AMExtend ifuPcAdderTest to cover regular opcodes and two byte jumps.May 13, 1979 5:12 PMAdd ifuChaose.May 3, 1979 3:18 PMMove stack manipulation & vm fix-up code to different part of loop in ifuPcAlphaPipeTest.May 3, 1979 2:56 PMAdd call to resetIfu after initIfuM1Thru3 in ifuPcAlphaPipe test.May 1, 1979 5:08 PMAdd sundry comments.April 27, 1979 5:19 PMAdd call to resetIfu from within ifuPcAlphaPIpe test.April 26, 1979 5:10 PMRemove initIfuCache thru ifuTestLoop--moved into ifuTestSubrs.mc.April 26, 1979 10:18 AMAdd code to use iUsingInstrSet during getCDbyte, putCDbyte; modify the code that puts opcodes inmemory to place them in virtual order, Jtest.April 25, 1979 12:52 PMMake iFastTest accessible to normal testing. (no longer infinite loop).April 24, 1979 3:49 PMAdd Pc adder test.April 24, 1979 9:19 AMAdd ifuTestLoop.April 24, 1979 8:46 AMAdd PcPipe test, and checkPcX routine & concomitant support code; add top level calls on varioustests so that control no longer "falls through".April 22, 1979 5:25 PMMove ifuBackground thru ifuCountOnes into ifuRamSubrs.April 20, 1979 6:09 PMFix missing "composeIfuWd[] in getIfuHalt.April 20, 1979 3:59 PMFix register clobbering bug in putIfuWd (another, different one).April 19, 1979 4:59 PMFix stack manipulation bug in ifuBackGround.April 19, 1979 11:38 AMAdd comments to ifuOpcode Test, diddle various things.April 11, 1979 9:53 AMFix register clobbering bug in putIfuWd.April 10, 1979 2:37 PMRearrange code to fit into functional categories -- prelude for division into different files.April 4, 1979 11:28 PMAdd test controls to iterate thru the various tests in memory.April 4, 1979 6:05 PMSet memBX to zero, disallow wakeups on single memory errors, cause FastTest to invoke resetIfusubroutine.March 1, 1979 7:17 PMAdd reschedule test.March 1, 1979 6:26 PMChange appendPause to appendHalts (3 words, 6 bytes), replace all pause opcodes with halts.February 17, 1979 6:12 PMAdd noops for placement.February 7, 1979 9:03 AMFlush the first munch of ifu program from cache.February 6, 1979 3:00 PMModify initialization to set All the words in Ifu memory to valid parity (pointing to aninstruction that causes the processor to get an error).February 6, 1979 2:15 PMFix bug in construction of program at 400 in memory; add noop after pcF_ before next ifuJump.February 5, 1979 10:36 AMAdd fast opcodes, program to memory, etc.January 29, 1979 10:52 AMAdd code to iMem that inits Ifu's code base.January 26, 1979 4:18 PMChange iMem to background memory so that the first memory referenes of the ifu code won't causetask 17 wakeups if there's garbage in storage. Remove mesa opcode stuf described below.January 22, 1979 6:04 PMFix bugs in memory checking code...add code that loads ifu memory w/ mesa opcode values. This isstrictly a hack to find out how to hand load ifumemory while the micro/microd/midas interface doesn'twork.January 22, 1979 11:02 AMFix mos_ bug, change default pcF, background storage with identity and cause the processor to make!dgp)b:N1bAq a1_B ^1]K \1ZY Y1XUA W1U T1S_5 R"1PA O1Ni` M,- K1JG Is1H6 F1E D}1C@` B0 @1?6 >J1= * ;1:A 9T18, 6156 4^13 ( 110^ /h1.*> ,1+^ *r )41' &1%|[ $>1# !1 0 H1 X 7 1R] 1) 1\, 1` X f1)a e  p1 3b $ D]$Ifu3a.mcMay 20, 1981 3:10 PM%3memory references, and check for correctness.January 22, 1979 9:44 AMAdd noops to remove very long ring: placement problem.January 22, 1979 9:18 AMAdd incClock calls into ifuJump looop; fix problems w/ program at wd 100; add more comments.January 20, 1979 8:28 AMFix putIfuWdPe0 bug, add more "programs" to cache.January 17, 1979 2:59 PMExecute from instruction set 3 (because exception addresses get instrSet' or'd into them). January 10, 1979 4:50 PMmore opcodes into ifuMemory, more programs into cache, stack+1_ID January 9, 1979 4:51 PMicStartIfu loop to reset ifu, pcF before beginning icTopL loop January 2, 1979 11:12 AMlongWait in initIfuCache to avoid memory system misses%!dgp)b:N bAq- a1_6 ^1]K] \1Z2 Y1WZ U1TA R1Q> O1N6 Mr L@TIfu3a.mcMay 20, 1981 3:10 PM%4* May 20, 1981 3:19 PMbeginIfu3a:pushReturn[];expectedDispatch_a1;call[ifuPcAlphaPipe];* check the data bits of the pc pipecall[ifuXqtTest];* try various programsendIfu3a:returnP[];!dgp)b:N bAq _p 1^q 1]K1Z$1Y XUp1Wq U)T;Ifu3a.mcMay 20, 1981 3:10 PM%5* June 5, 1979 11:33 AM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuPcAlphaPipeThis test checks the data bits of the Pc pipe, and the data bits of the alpha/H pipe. Proceed bygenerating different patterns to set into PcFG. After waiting enough time for the Ifu Pipe to fill,perform an Ifu jump and then look at PcX. It should have the same value we originally set into PcFG.Use a two byte opcode and cycle through all possible bit patterns in a byte for the second (alpha)byte.Don't forget to initialize the byte in memory pointed to by the pattern (and to undo setting that byteafterwards). We'll use instruction set 1, and make use of opcode = 1. This opcode gets used by the"test register" mode diagnostics that appear in Ifu1.mc.call[initIfuCache];--init the memory system for use by this testcall[initIfuMem1Thru3];FOR pat IN PatX DOoldByte _ getByte[pat];-- remember the original value where we put opcodeoldByte2 _ getByte[pat+1];-- original value where we put operand (alpha)putByte[pat,1];-- write opcode = 1 at byte location = patFOR bytePat IN [0..400B) DOputByte[pat+1, bytePat];PcFG _ pat;cnt _ 20;returnLink _ @ L1;Jump:IFUJUMP[0];L1:IF cameFromLocation # ExpectedLocation THENIF cameFromLocation = notReadyLocationTHEN GOTO JumpELSE SIGNAL IfuPcAlphaJumpErr[];putByte[pat, oldByte];-- restore memory to original valueIF PcX # pat THEN SIGNAL PcPipeErr[];IF IfuData # bytePat THEN SIGNAL AlphaPipeErr[];ENDLOOP;putByte[pat, oddByte];-- restore the opcode byteputByte[pat+1, oddByte2];-- restore the operand byte (alpha)ENDLOOP;%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++* June 5, 1979 11:33 AMifuPcAlphaPipe:pushReturn[];call[initIfuCache];* initialize the memory systemcall[resetIfu];call[setIUsingInstrSet], t _ 1C;noop;* for placementcall[resetIfu];call[initIfuM1Thru3];* init instrset1, IFUM 1-3call[resetIfu];* clear breakpending (from writing IfuM)call[enableConditionalTask];call[iPat16];ifuPcPipeL:call[nextPat16];skpif[ALU#0];branch[ifuAfterPcPipe];noop;* for placement.call[getCDbyte];* enter w/ t = byte addr, rtns t =stack+1_t;* contents of that byte location.call[getPat16];stack+1_t;* remember current pattern in stackcall[putCDbyte], rscr_2C;* use opcode = "2"call[iPat8];ifuPcAlphaL:* see if there are more byte patternscall[nextPat8];* for the current PcF value!dgp)b:N bAq a?)b_p ^qa ]Kd \e Zb Y Wf Ud T8 R"- P ONi" 2M,$.J*IsH6F ED}C@B @?+>J&= ;:&#9T%8065" 4^" #3  0? .* +p*rq )4+'&%|+$>#+!+( H  p q R++"\ +! +#f+ pp +q% 3+ D E3]%Ifu3a.mcMay 20, 1981 3:10 PM%6skpif[ALU#0], rscr _ t;* save byte pattern in rscrbranch[afterIfuPcAlphaL];noop;call[putCDbyte], t _ (stack)+1;* set "alpha" for this opcode. t = addr, rscr = bytevalue.PcF _ stack;* now test the Pc pipet _ 20C;cnt_t;* try no more than 20B timescall[ifuPcPipeSetJRet];* set up return link so we can getifuPcAlphaJump:IfuJump[0];* from our ifu jump.ifuPcPipeCont:* afterDispatch leaves rscr=location(rscr) # (opAt15);* where IfuJump took us.skpif[ALU#0];branch[ifuPcAlphaCheck];loopUntil[CNT=0&-1, ifuPcAlphaJump];ifuPcAlphaJumpErr:* after 20B times we should succeed inerror;% executing the opcode (the afterDispatch code takesaround 8 cycles). Since that hasn't happened, something is sadly amiss. RSCR=address where Ifudispatched the processor. Dispatches to notReady suggest the IFU can't talk to the memory system;other exception conditions speak for themselves.%ifuPcAlphaCheck:t _ not(PcX');t # (stack);* see if PcX matches our patternskpif[ALU=0];ifuPcPipeErr:* PcX should be (stack) and is (t).error;* data path error or control error.call[getPat8];rscr _ ID;(rscr) # t;skpif[ALU=0];ifuAlphaPipeErr:* rscr = ifuData, t = expected dataerror;t _ t-t;rscr _ (ID)+t;* force ID arithmetic patht _ (2c);t # (rscr);skpif[ALU=0];* should get instruction length (2)ifuAlphaPipeErr2:* rscr = IfuData, t = bad bits. Expected 2error;branch[ifuPcAlphaL];afterIfuPcAlphaL:stkp-1;* position stack to old bytet_stack&+1;* put the old value back into memoryrscr _ t;call[putCDbyte], t_stack;branch[ifuPcPipeL], stkp-2;* don't forget pattern & old byte are on stack.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuPcPipeSetJRetThis subroutine sets KLINK to point to an instruction that will GOTO ifuPcPipeCont. This is how wegive control back to the PcData routine after an IfuJump.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuPcPipeSetJRet:pushReturn[];call[ifuPcPipeSetJRet2];t _ link;klink _ t;returnP[];ifuPcPipeSetJRet2:coreturn;branch[ifuPcPipeCont];!dgp)b:NbAq+a_]K+5 \Y +XUW+U+" TpS_q + Pp +q$O+Ni M,K$ Jp+q&Is+4 H6` Fb E0 D} Bp@q ? +>J = p +q#;+#9T 8 6 5 4^p+q#3 0/h +.*, + +# *rp+q*)4& $>p!q+ +$H +/ R?(p qc 9 \? pq f)  p pq 3 D1].Ifu3a.mcMay 20, 1981 3:10 PM%7ifuAfterPcPipe:top level;call[disableConditionalTask];returnP[];!dgp)b:N _^q ]K\ ` X2c&Ifu3a.mcMay 20, 1981 3:10 PM%8* January 22, 1979 6:21 PM%ifuXqtTestTest the ifu using the memory system cache.The IfuOpCode Test sequences through a group of small 'programs' written into memory. The outerloop, whose top is at icNextTest controls which program the test executes. The inner loop whose topis at icNextTestIteration, controls how many ifuJumps the test executes before starting the next test.The inner loop has two phases. The first performs a simple IfuJump and then pushes ID onto the stack(the operator must look at the stack contents to decide it they (the contents) are correct. Thesecond phase exercises the memory system as well as the ifu. It performs a fetch at the same time itexecutes an IfuJump. If the data returned from that fetch is not the same as the data returned from asubsequent fetch from the same address, an error has occured. Then the test increments a rovingpointer that is forced to stay in the interval [100000B..177777B]. The memory initialization code haswritten that section of memory with its address (ie., location 135555 contains 135555, etc). The testfetches the contents of memory pointed at by the roving pointer (and complains if the contents is notequal to the address), and stores the address in that location (ie., rewrites the data).initIfuCache[];resetIfu[];rovingPtr _ 100000BFOR test in TestX DOPcF_getCurrentProgramLocation[test];FOR ifuJumpX IN IterationCount DOReturnLink _ @L1;-- return to L1 after ifufJumpIfuJump[0];L1:pushIDontoStack[];-- eyeball it to see if it is okpopIDfromStack[];IF PcX < getBeginLoc[test] or PcX > getEndLoc[test] THEN ERROR;IF (ifuJumpX _ IfuJumpX+1) ~IN IterationCount THEN GOTO EXIT;ReturnLink _ @L2;-- return to L2 after ifufJumpIfuJump[0], tempAddr _ FETCH_ID;L2:tempV _ MD;pushIDontoStack[];-- eyeball it to see if it is okpopIDfromStack[];IF PcX < getBeginLoc[test] or PcX > getEndLoc[test] THEN ERROR;FETCH_tempAddr;IF MD # tempV THEN ERROR;rovingPtr _ rovingPtr+17B;-- cross munch boundaries & everythingIF rovingPtr>0 THEN rovingPtr _ 100000B;-- only look at top half of memoryFETCH_rovingPtr;IF (MD#rovingPtr) THEN ERROR;STORE_rovingPtr, DBuf_rovingPtr;ENDLOOP;EXIT:%!dgp)b:N bAq a_p +q+^` ]Kp qD \pqM Ye XU` We Uf T` S_f R"f Pe OX M, K J IsH6$F!E+D} C@B+@??>J=;+:9T8 6+54^?3 10+&/h(2".*,+*r)4 & %YE3BIfu3a.mcMay 20, 1981 3:10 PM%9* September 18, 1979 11:09 AMifuXqtTest:pushReturn[];call[initIfuCache];* init the environment:*the memory system, the ifu memory, the cachecall[setIUsingInstrSet], t _ 3C;noop;* space for breakpoint so we can easily patch code.call[enableConditionalTask];icStartIfu:* reset the ifu, set pcFcall[resetIfu];t _ (r0)-1;clockCount _ t;icSetInstrSet:t _ 101400C;* instruction set 3MOS _ t;noop;* patch to B_t???call[initItest];icNextTest:call[nextITest];skpif[ALU#0];branch[icTestDone];noop;PcF _ t;* start IFU at current location.call[initITestCount];icNextTestIteration:call[nextITestCount];skpif[ALU#0];branch[afterTestCount];icTopL:* top of ifuJump loopnoop;* for placementcall[incClock];call[icGetResumeLoc];t _ link;klink _ t;* afterdispatch uses klink as a return linkifuJump[0];* control will eventually reach afterDispatchicResume:noop;* place for Severo to patchstack+1 _ ID;* in the worst case (len=3, packed alpha,stack+1 _ ID;* n#17) we must perform 5 _IDs to suckstack+1 _ ID;* the pipe dry and get one IL.stack+1 _ ID;stack+1 _ ID;icDownStack:noop;* can check the stack herestkp-4;stkp-1;call[checkPcX];* see if PcX is incorrect (approximateskpif[ALU=0];* check, only)icPcXErr1:* PcX is not within the range of theerror;% program we are currently executing. Ie., we'reexecuting an opcode from a memory location NOT in the program we should be executing.T = current PcX, RSCR = program begin location, RSCR2 = program end location.%call[nextITestCount];* see if we're done executing this testskpif[ALU#0];branch[afterTestCount];icSkipMemOps:* noop to patch if requirednoop;call[icGetResume2];t _ link;!dgp)b:N bAq _p ^q ]K+ \,ZXU+3W Tp +qS_R" P Nip M,q +KJ+Is Fp EqD} C@B@+>J ;p:q9T 8 5p+q4^+3 10.* ++, +p +*rq+)4 +)' +&& +%| $> #p !q+ H+& + Rp +q$+1 U M \+' f p +q  p 3l B-]&Ifu3a.mcMay 20, 1981 3:10 PM%10klink _ t;ifuJump[0], stack+1 _ (FETCH _ ID);icAfterJump2:noop;stack+1 _ MD;stack+1 _ ID;* in the worst case (len=3, packed alpha,stack+1 _ ID;* n#17) we must perform 5 _IDs to suckstack+1 _ ID;* the pipe dry and get one IL.stack+1 _ ID;stack+1 _ ID;stkp-4;stkp-1;call[checkPcX];* see if PcX is incorrect (approximateskpif[ALU=0];* check, only)icPcXErr2:* PcX is not within the range of theerror;% we are currently executing. Ie., we're executingan opcode from a memory location NOT in the program we should be executing.T = current PcX, RSCR = program begin location, RSCR2 = program end location.%t _ stack&-1;* retrieve old MD value from stackfetch _ stack;rscr _ MD;(rscr) # t;skpif[ALU=0];icMdErr:* t = data after fetch_id, rscr = dataerror;* after fetch_stack (where stack contained earlier id)stkp-1;rscr3 _ (rscr3) + (17C);* use large increment so we can move thruskpif[ALU<0];* entire cache reasonably quickly.rscr3 _ 100000c;* allow diagnostic to use va[0..77777B]fetch _ rscr3;t _ md;t # (rscr3);skpif[ALU=0];icMd2Err:* expect mem[va] = va for va>77777error;* used rscr3 for va, got md into t.store _ rscr3, Dbuf _ rscr3;branch[icNextTestIteration];afterTestCount:branch[icNextTest];icTestDone:call[disableConditionalTask];returnP[];icGetResumeLoc: subroutine;* return w/ link pointing to icResumeLoccoreturn;icResumeLoc:* we come here from afterDispatchbranch[icResume];icGetResume2:coreturn;icResume2:branch[icAfterjump2];%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++checkPcXThis subroutine returns ALU=0 IF PcX is within the range of the "current" program in memroy.Otherwise it returns ALU#0. In either case, it returns with T=PcX, rscr = program begin location andrscr2 = program end location.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++checkPcX:pushReturn[];call[getTestBounds];* returns w/ rscr = begin location, RSCR2=t_not(PcX');* end location.!dgp)b:NbAq _# ^p ]Kq\ Z +)Y +&XU +W U TS_P+&O + Nip +q$M,+4 KK JM IsF +"E D} C@ B @p+q&?+6= :+)9T +"8+'5 4^3 1 0p+q"/h+#.*+ )4p'q &p %|q$> !pq +(  Hp +qp  q p q Rp q B+f\p q\ e  fB p q  p+* 3 + D]-Ifu3a.mcMay 20, 1981 3:10 PM%11t-(rscr);skpif[alu>=0];branch[checkPcXFail];(rscr2)-(t);skpif[alu>=0];branch[checkPcXFail];returnPAndBranch[0C];* no errorcheckPcXFail:returnPAndBranch[1C];!dgp)b:NbAqa _^ ]K \Z+ Yp XUq X2&;Ifu3b.mcJune 18, 1981 10:13 AM%1%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Table of ContentsOrganized by Occurence of subroutine in this ListingSubroutineFunction+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++beginIfu3b:"main control", it calls the test subroutinesifuPcAdderTest:Force worst case carry propogation thru Ifu's adderiMiscEffects:Check miscellaneous side-effects, etc of IfuJumpiFastTest:Fast execution test (ifuJumps happen immediately)%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%June 18, 1981 10:13 AMFix bug in iMisc8-14....using wrong linkage for ifujumps.June 17, 1981 3:43 PMAdd test for Amux, Bmux checkout for IfuDataMay 27, 1981 11:42 AMAdd Fetch_ID test to iMiscEffects.May 20, 1981 3:21 PMConstruct this file out of ifu3.mcMay 19, 1981 4:50 PMBegin adding iMiscEffects test (for RestoreStkP, IDFetch_, Fetch_ID, etc.)February 1, 1980 8:05 PMFix miscellaneous comments, fix performance bug in iFastTest.September 19, 1979 1:14 PMSet expectedDispatch<0 in beginIfu3 -- for robustness.September 18, 1979 11:07 AMCause tests that enableConditionalHold to disableConditionalTask as well -- seem to havemysterious bug that is associated with tasking. Fix some comments in IfuXqtTest....July 3, 1979 2:08 AMAdd noops for placement purposes. -- apparently setIUsingInstrSet causes some problems....June 5, 1979 11:40 AMAdd calls to enableConditionalTask...May 30, 1979 10:16 AMExtend ifuPcAdderTest to cover regular opcodes and two byte jumps....April 26, 1979 5:10 PMRemove initIfuCache thru ifuTestLoop--moved into ifuTestSubrs.mc....Make iFastTest accessible to normal testing. (no longer infinite loop).April 24, 1979 3:49 PMAdd Pc adder test.% gp(:N bAqB(`ap_4^q "  ]K?\p " q-Zp" q3Yp " q0XUp " q1 WB T S_1R"9 P1O, Ni1M," K1J" Is1H6J F1E= D}1C@6 B1@X ?Q >J ;1:W 8 514^" 1 /h1.*B + )41'A %|1#G !1  H >FJ#Ifu3b.mcJune 18, 1981 10:13 AM%2* May 20, 1981 3:21 PMbeginIfu3b:pushReturn[];expectedDispatch_a1;call[ifuPcAdderTest];* find out if jumps involving many carry propogates workcall[iMiscEffects];call[iFastTest];endIfu3b:returnP[]; gp(:N bAq _p 1^q 1]K1Z81Y1XU Wp1Uq Tz6<Ifu3b.mcJune 18, 1981 10:13 AM%3* June 5, 1979 11:35 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++IfuPcAdderTestSee if the logic that performs jumps works properly when worst case carry conditions obatain. Theidea is to have a loop that bounces back and forth between location 0 and location 177777B. There arethree test cases: use one byte jumps, use two byte jumps and use a jump and a one byte normal opcode(the jump gets the Pc to the 17777X range and the normal opcode gets the Pc to 0).%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuPcAdderTest:pushReturn[];call[initIfuCache];call[setIUsingInstrSet], t _ 3c;noop;* for placement.call[enableConditionalTask];FETCH _ r0;* save contents of word 0, word 7777 instack+1_MD;* the stack.t _ 77777C;FETCH_t;stack+1 _ MD;ifuPcAdder2:% Test 2 involves two one byte jumps, one at location0 and the other at location "-1":Pc (byte addres)Contents of byte++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++0one byte jump .-1177777one byte jump .+1++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%t _ (r0);rscr _ jumpM1;* one byte (jump .-1) in byte 0,call[putCDbyte];* one byte (jump .+1) in byte 177777Bt _ 177777C;* remember, it is instruction set 3rscr _ jump1;call[putCDbyte];t _ 2c;* begin with test 2.stack+1 _ t;* there are 3 tests we'll perform. keep test indicatorin top of stackifuPcAdderReset:* Top of the test loop.call[resetIfu];PcF_r0;call[ifuSetPcCont];call[initITestCount];ifuPcAdderL:* within each test, after an IfuJump,call[nextITestCount];* control comes hereskpif[ALU#0];branch[afterIfuPcAdder];ifuJump[0];ifuPcAdderCont:branch[ifuPcAdderL];ifuSetPcCont:* set KLINK so that this test can regainpushReturn[];call[ispc];* control from afterDispatch.t_link;klink_t;returnP[];ispc:coreturn;branch[ifuPcAdderCont]; gp(:N bAq aB)b_p ^qb ]Kf \d ZR YB WpUq TS_R"+PNi +'M, + K JIs Fp +q5 E!C@+ B@@+?+ >J@ = ;: +!9T+&8 +#6 54^+3 +6 1 /hp+q.*,+)4 'p +q%&+%| $>! pHq p +q( R + \pq> E3VIfu3b.mcJune 18, 1981 10:13 AM%4* February 1, 1980 8:04 PMtop level;afterIfuPcAdder:PD _ stack _ (stack)-1;* see if we're done w/ tests;branch[ifuPcAdderXit, ALU<0], PD _ stack;branch[IfuPcAddr0, ALU#0];* currently on test 1ifuPcAdder1:% Test 1 involves a 2 byte jump at location zero tolocation "-3" where there are 3 one byte, normal opcodes:Pc (byte addres)Contents of byte++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++02 byte jump opcode, sign extended1-3177775one byte, regular opcode177776one byte, regular opcode177777one byte, regular opcode++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%t _ cm1;call[putCDbyte], rscr _ opNoop;t _ cm2;call[putCDbyte], rscr _ opNoop;t _ 177775C;* -3call[putCDbyte], rscr _ opNoop;t_A0;call[putCDbyte], rscr _ jumpML2;t _ 1c;call[putCDbyte], rscr _ 177775c;* 2 byte jump to .-3 at location 0branch[ifuPcAdderReset];ifuPcAddr0:% test 0 involves two 2 byte jumps between location 0and location -2:Pc (byte address)Contents of byte++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++02 byte jump, sign extended1"-2"1777762 byte jump177777"2"++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%t _ A0;call[putCDbyte], rscr _ JumpML2;t _ 1c;call[putCDbyte], rscr _ cm2;t _ cm2;call[putCDbyte], rscr _ jumpL2;t _ cm1;call[putCDbyte], rscr _ 2c;branch[ifuPcAdderReset];ifuPcAdderXit:* done with all our testst _ 77777C, stack&-1;* fix stack which has current test number on it, and then restore clobberedmemory locations.STORE _ t, DBuf _ stack&-1;t_r0;STORE_t, DBuf _ stack&-1;call[disableConditionalTask];returnP[]; gp(:N bAq_ ^p]Kq+\)Z+ Yp +q3 XU9U+ T@S_+!R"+P+O+Ni+ M,@ KJIsH6FE +D}C@B@?+">J = p +q5 ;9T+ 8@6+5+4^+ 3 + 1@ 01/h1.*1,1+1*r1)41'1&1%| #p q1!K 1H1 111R N DlOIfu3b.mcJune 18, 1981 10:13 AM%5* May 27, 1981 11:41 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++MiscEffectsThis test checks that miscellaneous effects associated with an IFUjump work properly:IDFetch_ must work.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iMiscEffects:pushReturn[];%Test RestoreStkP.The basic idea is to set StkP to one value, do an IFU jump, set StkP do a new value then to doRestoreStkP. Then StkP should be equal to the original value. We check for original value = 1 andoriginal value=376. There is an implementation problem with this test: the afterDispatch codeinsists upon writing into the Stack at StkP+1! thus we preserve the value at Stack[2] which is thestack location that will be clobbered when afterdispatch gets control (and StkP=1). We don't careabout the other location because it is so "high" in the stack that we never use it.rscr3_ current stkp,rscr4_ value of stack[2]%call[initIfuCache];call[setIUsingInstrSet], t_3c;t_ (r0)+1;* for placement.call[setPcF200], rscr4_ t+1;* keep "2" in rscr for a momentrscr3_ Tioa&StkP;call[setStkP], t_ rscr4;* stkp=1 when IfuJump happensbranch[getiMisc1Cont], rscr4_Stack&-1;* rscr4_ Stack[2]iMiscJ1:* get here from getiMisc1Cont.IfuJump[];* processor should save StkP as it executes thisIfuJumpiMisc1Cont:* get here from AfterDispatch.call[setStkP], t_ a1;* now set StkP to a different valuecall[iMiscGetStkP], RestoreStkP;* processor restores old StkPt # (1c);* original value was 1skpif[alu=0];iMiscErr1:* RestoreStkP did not restore userror;* to zero, the value before ifujump* Now try the same thing, but use different values for StkP.call[setStkP], t_ 376C;call[setPcF200];branch[getiMisc2Cont];iMiscJ2:IfuJump[];iMisc2Cont:call[setStkP], t_a0;call[iMiscGetStkP], RestoreStkP;t#(376C);skpif[alu=0];iMiscErr2:* RestoreStkP did not restore us toerror;* 376B, the value before IFU jump.* Restore the original value of Stack[2], StkP, then return.call[setStkP], t_ 2c;t_rscr4;Stack_ t;StkP_ rscr3; gp(:N bAq aB*d_p ^qU \ ZB XUp Wq U T R"^ Pc O_ Nib M,b KSIsH6 FED}C@ +B+@?+>J&+ ;p+q: +0 9T 6p q+5+#4^+3 +1 0pq+/h+# ,<*r)4' &p%|q $>p q#! H  p +q#+" R<\  C/UMIfu3b.mcJune 18, 1981 10:13 AM%6* May 27, 1981 3:15 PM%Test Fetch_ID. We assume Store_Id will work if Fetch works. The idea is to execute an ifujump for a3 byte instruction w/ alpha=377C and beta=0.First we set BrLo=377 THEN perform Fetch_ID. The pipeVa ought to be 377+377.We check for correct ID, correct Va, correct Md.Set BrLo to zero and perform Fetch_ID. Check PipeVa, Id, Md.%t_1000C;* use byte location 1000call[putCDbyteAddr];call[putNextByte], t_ opNoopL3;* Use 3 byte instruction w/call[putNextByte], t_ 377C;* ENCODED CONSTANT=3 (throw it away)call[putNextByte], t_ a0;* alpha=377B, beta=0call[setPcF1000];t_377C;BrLo_t;call[longWait],t_10C;branch[getiMisc3Cont];iMiscJ3:IfuJump;iMisc3Cont:t_Id;* throw away encoded constant.t_ (Fetch_Id);rscr_a0;BrLo_rscr;t#(377C);* first id should be 377skpif[ALU=0];iMiscErr3a:error;* got incorrect Id (t)rscr_VaLo;t_ t+t;t#(rscr);skpif[ALU=0];iMiscErr3b:* va is wrong in pipe. should be 377+377error;Fetch_t, rscr_Md;(Md)#(rscr);skpif[ALU=0];iMiscErr3c:* data from memory is wrongerror;* Try it again, only use ID=beta=0t_ (Fetch_Id);Pd_t;* SECOND id should be 0skpif[ALU=0];iMiscErr4a:error;* got incorrect Id (t)rscr_VaLo;skpif[ALU=0];iMiscErr4b:* va is wrong in pipe. should be 0error;Fetch_t, rscr_Md;(Md)#(rscr);skpif[ALU=0];iMiscErr4c:* data from memory is wrongerror; gp(:N bAq a _e ^, \M Z0 XU= UT+S_R"+P+$O+NiKJIsH6 FpEq D}p C@q+B @? >J+= ;p :q+8 654^ 3 p +q(1/h.* , +p +q*r '"& %|+rq$> #p !q+H  p +q"  \p +q2 DVIfu3b.mcJune 18, 1981 10:13 AM%7* May 28, 1981 9:04 AM%Test Ifetch_ code.Ifetch_ works by replacing the low 8 bits of the current base register with ID. Consequently theaddress computed by the memory system is the valueBR[0..23],,Id+Mar. Ie., the concatenation of the high bits of the current base register with Id plusthe value on Mar.Set the low 8 bits of BR to zero and non-zero values to see if Ifetch replaces those bits with Id.%call[setPcF1000];*This test uses BR=0branch[getiMisc5Cont];iMiscJ5:IfuJump;iMisc5Cont:t_a0, RisID;* throw away encoded constantIFetch_t;* Ifetch does not advance IFUdatat_Id;* thus, this ID is same as one for IFetcht#(377C);* first id should be 377skpif[ALU=0];iMiscErr5a:error;* got incorrect Id (t)rscr_ VaLo;(rscr)#t;* t=idskpIF[alu=0];iMiscErr5b:* Low bits of va should be 377=IDerror;Fetch_t, rscr_ Md;(Md)#(rscr);skpif[ALU=0];iMiscErr5c:error;* test IFetch with brlo=377, ID=0 (means va should be zero)t_377c;BrLo_t, t_a0;IFetch_t;* IFetch does not advance IfuDatat_ Id;* thus, this ID is same as one for IFetchrscr_a0;BrLo_rscr, Pd_t;skpif[ALU=0];* ID should be zero!iMiscErr6a:error;* got incorrect Id (t)rscr_ VaLo;(rscr)#t;* t=idskpIF[alu=0];iMiscErr6b:* Low bits of va should be 0=IDerror;Fetch_t, rscr_ Md;(Md)#(rscr);skpif[ALU=0];iMiscErr6c:error; gp(:N bAq a _ ]Ka \3 Ze Y Wb US_+R" PpOq Nip M,q +K+!J+)Is+H6 Fp Eq+C@ B+@ ?p +q!>J;: 9T 8p 6q 4^;10 /h+!.*+),+*r + )4p 'q+%| $>+# !p +q    Rp q DPWIfu3b.mcJune 18, 1981 10:13 AM%8* June 18, 1981 10:12 AM% This test checks that RM & T, Amux and BmuxThe idea is to test the following sets of actions:t_ A_ ID, B_ opposite bits from IDRM_ A_ ID, B_ opposite bits from IDT_ B_ ID, A_ opposite bits from IDRM_ B_ ID, A_ opposite bits from ID%call[setPcf1000];call[getiMisc7Cont];iMiscJ7:IfuJump;iMisc7Cont:rscr_ a1;Pd_ Id;* throw away encoded constantPd_ Id;* throw away alpha byteT_ A_ Id, B_ rscr;* ID is all zerosskpif[ALU=0];iMisc7Err1:* should have id=t=0error;call[setPcf1000];call[getiMisc8Cont];iMiscJ8:IfuJump;iMisc8Cont:t_ a1;Pd_ Id;* throw away encoded constantPd_ Id;* throw away alpha byterscr_ A_ Id, B_ rscr;* ID is all zerosskpif[ALU=0];iMisc8Err1:* should have id=t=0error;call[setPcf1000];call[getiMisc9Cont];iMiscJ9:IfuJump;iMisc9Cont:rscr_ a1;Pd_ Id;* throw away encoded constantPd_ Id;* throw away alpha byteT_ T, TisID, A_ rscr;* ID is all zerosskpif[ALU=0];iMisc9Err1:* should have id=t=0error;call[setPcf1000];call[getiMisc10Cont];iMiscJ10:IfuJump;iMisc10Cont:t_ a1;Pd_ Id;* throw away encoded constantPd_ Id;* throw away alpha byterscr_ rscr, RisID, A_ rscr;* ID is all zerosskpif[ALU=0];iMisc10Err1:* should have id=t=0error;t_1000C;* use byte location 1000call[putCDbyteAddr];call[putNextByte], t_ opSign3;* Use 3 byte instruction w/ sign bit, no encodedcall[putNextByte], t_ 377c;* constant. alpha byte=377=>ID=-1=177777C call[setPcf1000];call[getiMisc11Cont];iMiscJ11:IfuJump;iMisc11Cont:rscr_ a0; gp(:N bAq _- ^2]K"\#Z#Y# XUWU TpqS_ R"p qPO+Ni+M,+K Jp +qIsFE D}pqC@ Bp q@?+>J+= +; :p +q9T65 4^pq3  1p q0/h+.*+,++ *rp +q)4&%| $>pq# !p q H+ ++ Rp +q+\+0++ f) pq  pp q 3 @)]>Ifu3b.mcJune 18, 1981 10:13 AM%9T_ A_ Id, B_ rscr;* ID is all onest # (177777C);skpif[ALU=0];iMisc11Err1:* should have id=t=all oneserror;call[setPcf1000];call[getiMisc12Cont];iMiscJ12:IfuJump;iMisc12Cont:t_ a0;rscr_ A_ Id, B_ rscr;* ID is all ones(rscr) # (177777C);skpif[ALU=0];iMisc12Err1:* should have id=t=all oneserror;call[setPcf1000];call[getiMisc13Cont];iMiscJ13:IfuJump;iMisc13Cont:rscr_ a0;T_ T, TisId, A_ rscr;* ID is all onest # (177777C);skpif[ALU=0];iMisc13Err1:* should have id=t=0error;call[setPcf1000];call[getiMisc14Cont];iMiscJ14:IfuJump;iMisc14Cont:t_ a0;rscr_ rscr, RisID, A_ rscr;* ID is all ones(rscr) # (177777C);skpif[ALU=0];iMisc14Err1:* should have id=t=all oneserror;returnP[]; gp(:NbAq+a _ ^p +q]KZY XUpqW Up qTS_+R"P Op +qNiKJ IspqH6 Fp qED}+C@ B @p +q?= ; :pq9T 8p q65+4^3 1p +q0.*  +2 <Ifu3b.mcJune 18, 1981 10:13 AM%10* May 28, 1981 1:11 PM* miscellaneous subroutines for iMisc tests.setPcF200: subroutine;t_200C;PcF_t, RETURN;setPcF1000: subroutine;t_1000c;PcF_t, RETURN;setStkP: subroutine;StkP_t, RETURN;top level;getiMisc1Cont:call[iMisc1Setup];klink_ link, branch[iMiscJ1];iMisc1Setup: subroutine;coreturn;branch[iMisc1Cont];top level;getiMisc2Cont:call[iMisc2Setup];klink_ link, branch[iMiscJ2];iMisc2Setup: subroutine;coreturn;branch[iMisc2Cont];top level;getiMisc3Cont:call[iMisc3Setup];klink_ link, branch[iMiscJ3];iMisc3Setup: subroutine;coreturn;branch[iMisc3Cont];top level;getiMisc5Cont:call[iMisc5Setup];klink_ link, branch[iMiscJ5];iMisc5Setup: subroutine;coreturn;branch[iMisc5Cont];top level;getiMisc7Cont:call[iMisc7Setup];klink_ link, branch[iMiscJ7];iMisc7Setup: subroutine;coreturn;branch[iMisc7Cont];top level;getiMisc8Cont:call[iMisc8Setup];klink_ link, branch[iMiscJ8];iMisc8Setup: subroutine;coreturn;branch[iMisc8Cont];top level;getiMisc9Cont:call[iMisc9Setup];klink_ link, branch[iMiscJ9];iMisc9Setup: subroutine;coreturn;branch[iMisc9Cont];top level;getiMisc10Cont:call[iMisc10Setup]; gp(:N bAq a, ^p q ]K\ Zp q YXU Upq TR" Pp OqNi M,p q KJH6 Fp EqD} C@p q B@>J = p ;q: 9Tp q 864^ 3 p 1q0 /hp q .*,*r )4p 'q& %|p q $># Hp  q p q R \p q p q f) pp 3qj ] Ifu3b.mcJune 18, 1981 10:13 AM%11klink_ link, branch[iMiscJ10];iMisc10Setup: subroutine;coreturn;branch[iMisc10Cont];top level;getiMisc11Cont:call[iMisc11Setup];klink_ link, branch[iMiscJ11];iMisc11Setup: subroutine;coreturn;branch[iMisc11Cont];top level;getiMisc12Cont:call[iMisc12Setup];klink_ link, branch[iMiscJ12];iMisc12Setup: subroutine;coreturn;branch[iMisc12Cont];top level;getiMisc13Cont:call[iMisc13Setup];klink_ link, branch[iMiscJ13];iMisc13Setup: subroutine;coreturn;branch[iMisc13Cont];top level;getiMisc14Cont:call[iMisc14Setup];klink_ link, branch[iMiscJ14];iMisc14Setup: subroutine;coreturn;branch[iMisc14Cont];iMiscGetStkP: subroutine;t_ Tioa&StkP;RETURN, t_ t and (377C); gp(:NbAq ap q _^Z YpXUqW Up q TS_O NipM,qK Jp q IsH6D} C@pBq@ ?p q >J= : 9Tp8q6 5p q 4^3  0p q /h .* ,;AIfu3b.mcJune 18, 1981 10:13 AM%12* February 1, 1980 8:04 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Fast TestThis is a test that executes most ifuJumps very quickly. It "runs" the program written into wordlocation 200 in the memory. The program it runs consists of a sequence of six one byte opcodesfollowed by "failing" conditional jump followed by a loop to the top of the program.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iFastTest:pushReturn[];call[initIfuCache];call[setIUsingInstrSet], t _ 3c;noop;* for placement.call[enableConditionalTask];ifuTest _ r0;call[resetIfu];t _ (r0)-1;clockCount _ t;* for future use.t _ 101400C;* use instruction set 3iftSetInstrSet:MOS _ t;call[iftGetContinueLoc];t _ link;klink _ t;iftFlush:t _ 200c;rscr _ (Flush_t) + t;* flush our munch, compute byte addr.t _ 100c;call[longWait];* wait arbitrary time for flush to finish.t _ lastTestCountC;cnt _ t;* control how many times we'll loop.stkp+1;* increment stack so the opcodes won'tiftSetPcF:* clobber our return link.PcF _ rscr;noop;* wait for it to take effect.ifuJump[0];error;subroutine;;iftGetContinueLoc:coreturn;t _ cnt;PD_t;skpif[ALU=0];* quit if cnt=0ifuJump[0];afterIft:top level;call[disableConditionalTask];pReturnP[]; gp(:N bAq aB+_p ^qa ]K_ \T ZB Yp XUq WUTS_R" PO Ni K  JpIsqFED} Bp@q?'%>J=  *;:$9T& 8p q6 53 1/h .*p,q+*r)4 ' &p%|q $>#  !AFkIfu3c.mcJune 21, 1981 1:21 PM%1%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Table of ContentsOrganized by Occurence of subroutine in this ListingSubroutineFunction+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++beginIfu3c:"main control", it calls the test subroutinesiReschedTest:test Ifu reschedule for defered, non-deferred operationiRamPEtest:test ramPe exception conditionsifuChaos:Test randomly constructed opCodes.ifuBrkInsTestTest execution of opcodes sourced from BrkIns%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%June 21, 1981 1:21 PMFix ifuChaos to use POINTERS value saved by afterDispatch when checking Membase valuesJune 20, 1981 2:51 PMHave to set Jump bit in ifum for RamPe stuff, too.June 20, 1981 11:06 AMFinally found an IFU hardware design bug that causes RamPE exception to be forgotten ifReschedPending is true and the opcode after the one w/ the bad parity has good parity. Fix inmicrocode is to keep the pause bit logically true. That prevents J from loading valid data aftercausing a ram pe.June 18, 1981 1:53 PMAdd new section to iRamPEtest that actually executes ram pe jumps.June 18, 1981 10:24 AMAdd a call to longWait in iRamPEtest to avoid notReady dispatchMay 20, 1981 3:04 PMConstruct this file out of ifu3.mcMay 19, 1981 4:50 PMBegin adding iMiscEffects test (for RestoreStkP, IDFetch_, Fetch_ID, etc.)...Fix bug in ifuBrkInsTest -- failing to load BrkIns from left half of Bmux.August 1, 1979 3:24 PMInvert order of BrkIns_, Pcf_.August 1, 1979 11:11 AMRearrange parts of IfuBrkInsTest for easier scope looping.August 1, 1979 10:45 AMAdd noop to ifuBrkInsTest to accommodate placement problems.August 1, 1979 10:36 AMFix omitted initialization of ifu memory in ifuBrkInsTest, missking skip instr, set instrset inifu.August 1, 1979 9:28 AMAdd the ifuBrkInsTest, add misc. comments.July 3, 1979 2:27 AMfix stack underflow error in resched test.July 3, 1979 2:21 AMFix bug in iReschedTest -- clobbered the value that we load PcF with.July 3, 1979 2:08 AMAdd noops for placement purposes. -- apparently setIUsingInstrSet causes some problems.July 3, 1979 1:55 AMFix resched test, further, to handle the fact that reschedules don't occur after one IfuJump butafter several.July 3, 1979 12:37 AMCause iRamPEtest to enable the ramPE exception condition.June 29, 1979 5:02 PMFix ifuChaos' ID checking to preserve ID in a register rather than xoring it with the expectedvalue.June 29, 1979 11:54 AMCause ifuChaos to reset memBase and memBX inside the ifuChaosL; check ;Rbase immediately after theIfuJump (in ifuChaos), since afterDispatch leaves POINTERS in a very fragile place (stk+1).June 29, 1979 10:53 AMAdd missing "coreturn" at sicR2 (inside setIfuChaosRet).June 24, 1979 6:40 PMChange ifuChaos to use getIfuMBase, getIfuRBase for checking.June 19, 1979 9:53 AMFix stack bug in iRamtest.June 18, 1979 9:24 AMFix functional bugs in iRamPEtest (check for resched loc, reset rbase, membase, callsetUsingInsrSet.June 18, 1979 9:01 AM!gp) :rN bAqB(`ap_4^q "  ]K?\p " q-Zp " q7Yp " qXUp" q"Wp " q- UB S_ R"1PV O1Ni2 M,1KW J^ Isa H6 F1EB D}1C@? B1@" ?1>JJ ;19TJ 816 514^: 3 11< 01/h_ .* ,1+* *r1)4* '1&E %|1$>W #1!` H1 9 1^ R 1b [ \18 1= f1) 1 T p 3 D],Ifu3c.mcJune 21, 1981 1:21 PM%2Fix stack bugs in iRamPEtest.June 17, 1979 4:30 PMAdd iRamPEtest.June 6, 1979 10:30 AMChaos placement errors.June 5, 1979 11:40 AMAdd calls to enableConditionalTaskJune 1, 1979 6:16 PMFix ifuChaos errors....May 13, 1979 5:12 PMAdd ifuChaose....March 1, 1979 7:17 PMAdd reschedule test....%!gp) :rN1bAq a1_ ^1]K \1Z" Y1XU U S_1R" O Ni1M, J IsH HTIfu3c.mcJune 21, 1981 1:21 PM%3* beginIfu3c:pushReturn[];call[iReschedTest];call[iRamPEtest];call[ifuChaos];call[ifuBrkInsTest];endIfu3c:returnP[];* September 18, 1979 11:11 AM%RESCHED TestThis test checks that the ifu delays a normal resched by one successful ifuJump and that thereschedNow FF causes an immediate resched.resetIfu[];SetPcf[];Set resched.DOPerform an Ifu JumpIf dispatchLocation=resched OR dispatchLocation=Unknown THEN ERRORIf dispatchLocation=notReady THEN LOOP;EXIT;ENDLOOP;Perform an IfuJumpIF dispatchLocation#resched THEN ERRORSet reschedNowPerform an IfuJumpIf dispatchLocation#resched THEN ERROR;NoResched[];IfuReset[];%iReschedTest: subroutine;pushReturn[];call[initIfuCache];call[enableConditionalTask];call[resetIfu];call[setIUsingInstrSet], t _ 3c;noop;* for placement.t _ exceptions.Resched3;* this test accepts reschedule exceptionsexceptionsMask _ t;t _ 2c;iTestX _ t;* So that checkPcX will work on test 2t _ Test2MemByteLocC;* vanilla program (test 2)PcF _ t;call[getIReschedCont1];t _ link;reschedule[];klink _ t;iReschedL:IfuJump[0];iReschedCont1:* AfterDispatch leaves rscr= dispatch loc(rscr) # (is3reschedLocC);skpif[ALU#0];iReschedErr1a:* resched dispatch occured immediatelyerror;* after first ifuJump(rscr) # (opAt15);skpif[ALU#0];branch[iResched2];* got one successful ifuJump. try again.(rscr) #(is3notReadyLocC);skpif[ALU#0];* not ready only reasonable thing left.branch[iReschedL];* try again.iReschedErr1b:* unknown dispatch. wasn't (resched,error;* notReady, expected opcode).iResched2:call[getIReschedCont2];!gp) :rN bAq _p 1^q 1\1Z1Y1XU Wp1Uq T S_*R"p Pq] O* Ni M, K JIsH6BF'ED} C@ B& @ ? >J' = ; : 9Tp q 8 654^3 1+/h+).*+*r +&'+&%|$># ! p Hq  p +q) Rp +q&+\ +( +'f+ )p +q$ + pp  3q ?']$Ifu3c.mcJune 21, 1981 1:21 PM%4t _ link;klink _ t;cnt _ 2s;* should get resched after small numberiReschedL2:* of "normal" ifu dispatches.IfuJump[0];iReschedCont2:t _ rscr;* save rscr on stack, thencall[checkPcX], stack+1 _ t;* see if PcX indicates we're in correctbranch[iReschedBad, ALU#0], t _ stack&-1;* "program."rscr _ t;* Either we've come from not ready,(rscr) # (is3notReadyLocC);* a "normal" opcode, or a rescheduleskpif[ALU#0];branch[iReschedL2];* not ready yet. try again.(rscr) # (is3reschedLocC);* perhaps we've had a rescheduleskpif[ALU#0];branch[iResched3Init];* finally got the reschedule we wanted.loopUntil[CNT=0&-1, iReschedL2];* Small number of "normal" dispatches ok.iReschedErr2a:* Eventually should get resched dispatch.error;* Only got normal opcode dispatches.iReschedBad:* According to PcX, the last IfuJumperror;* executed an opcode NOT a part of the test program.T = return link for dispatch* Normal, delayed resched worked.!gp) :rNbAqa _+' ^p +q]K \p Zq+Y+'XU)+ U+#T+$S_ R"+O+Ni M,+'J+) Isp +q)H6+$ Ep +q$D}+4 C@ @! ?dD1(Ifu3c.mcJune 21, 1981 1:21 PM%5* March 2, 1979 9:05 AM* Test reschedNowiResched3Init:noReschedule[];* begin by clearing out the old onecall[resetIfu];ff256[103];* do reschedNow, setPcf and then IfuJump.t _ 100c;PcF _ t;call[getIReschedCont3];t _ link;klink _ t;IResched3:IfuJump[0];iReschedCont3:(rscr) # (is3reschedLocC);skpif[ALU#0];branch[iReschedTestDone];(rscr) # (is3NotReadyLocC);skpif[ALU#0];branch[iResched3];* try as long as its not readyiReschedErr3a:* after reschedNow we should get ONLYerror;* resched dispatch, not ready or* unexpected machine errors.iReschedTestDone:call[disableConditionalTask];noReschedule[];call[resetIfu];returnP[];* March 2, 1979 5:20 PMgetIReschedCont1:coreturn;branch[iReschedCont1];getIReschedCont2:coreturn;branch[iReschedCont2];getIReschedCont3:coreturn;branch[iReschedCont3];!gp) :rN bAq _ ]Kp \q+#ZXU +)WUTS_R" Pp Oq Nip M,qK JIsH6 F+ Ep +q%D}+C@ @p?q>J= ; 9T 8p6q5 4^p3 q1 0p/hq.*6 ,;u;AIfu3c.mcJune 21, 1981 1:21 PM%6* June 20, 1981 2:50 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iRamPeTestTest the ramPE exception logic.The first test generates real ram PEs and checks that the IFU actually dispatches the processor to theIFU ramPE location. It does this by setting the non-pe bits in the IFUM to all 0s or all 1s. Then itselects one of the three PE bits to have the WRONG value. When the processor executes an IFUJump, theIFU should dispatch the microcode to the appropriate ram pe location. USE reschedNow to guaranteethat we don't go off to some arbitrary location if the ram pe logic fails. Ie., We set reschedNowand when the IFUJump occurs, the processor will end up at the resched location UNLESS there is a ramPE. The second test employs reschedNow to force the IFU to dispatch the processor to a known location,regardless of the IM target address in the IfuM. This way many different bit patterns in IfuM can betested, without having to dedicate code in IM for ifu entrypoints for all possible IFAD (IM targetaddress, as stored in the Ram) values.iRamPEtest: PROCEDURE =BEGINFOR pat IN PatX DOlh _ getPat[patX];rh _ getPat[patX] AND (not ifu.PEmask);call[setRPEJret];FOR iAddr IN iAddrX DOputIfuWd[iAddr, lh, rh];--- write patterh w/ good parityreschedNow[];-- force immediate rescheduleputCDbyte[0, iAddr];-- write opcode into memorysetInstrSet[iAddr];PcFG _ 0;IfuJump[];RPEcont:IF wentTo # Resched THEN ERROR;ENDLOOP;-- try next address in IfuM w/ the current patternENDLOOP;-- try a new patternEND;setRPEJret: PROCEDURE =BEGINt _ @RPEcont0;klink_t;RETURN;RPEcont0:goto[RPEcont];END;%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iRamPEtest: pushReturn[];call[initIfuCache];call[disableConditionalTask];set[wantExceptionsRPE, OR[exceptions.RamPe3!, exceptions.RamPe2!, exceptions.RamPe1!,exceptions.RamPe0!]];t _ (and[wantExceptionsRPE,177400]C);t _ t or (and[wantExceptionsRPE, 377]C);exceptionsMask _ t;call[resetIfu];call[iIAddr], stkp+1;* we'll keep iAddr on stack;% This test checks the PE bits in IFUM. When ReschedPending is true the IFU hardware has a bug thatallows it to forget ram parity errors if the opcode in the pipe following the one with the parityerror has good parity. Consequently we force the Pause and Jump bits to be logically true (0). Thisway we guarantee that J will not fill up and that guarantees that the IFU will not forget the ramparity error. (When ReschedPending is true InstrAddrLd is true. This causes the IFU to reevaluatewhich exception dispatch it should generate. The ram parity error gets loaded into M during onecycle. Then, when J fills up with an instruction with valid parity, SawRamParityErr goes away and theexception dispatch changes from RamPE to Reschedule! Ugh. That was a hard two days.The practical consequence of this is that when we background the IFUM w/ all ones, iDoRamPe will zerothe Pause bit so we can use our reschedule trick. That means we must set PE2 appropriately for allones except for the pause bit; ie., we must set pe2 to 1 unless we want to check that bit itself. Thereschedule trick guarantees that we don't start executing some random IM location if the Ram PE logic!gp) :rN bAq a?*_p ^q \f Zf Yf XUb Wc Ud T R"d Pe Ob Ni& M,p q KJIsH6'FED}+C@ $B)z@?>J = ;:" 29T8 6p q 54^ 3 1 0p/hq .* +? )4p q @'@& %|U $>@#%@!(@ @H@+ R c b e \a b ` f fU e c pf 3e E3]Ifu3c.mcJune 21, 1981 1:21 PM%7fails -- we go to the reschedule location instead.%iRamPeL:call[nextIaddr];branch[iRamPeLXit, ALU=0], stack_t;rscr_ 4c;* ramPE is 3 bit field. test PE0 bitrscr2_ a0;* IFUM has all zerosiRamPeL0:* testing PE0 bitcall[iDoRamPE], t_ stack;rscr_ 5c;* ramPE is 3 bit field. test PE0 bitrscr2_ a1;* IFUM has all onescall[iDoRamPE], t_ stack;rscr_ 2c;* ramPE is 3 bit field. test PE1 bitrscr2_ a0;* IFUM has all zerosiRamPeL1:* testing PE1 bitcall[iDoRamPE], t_ stack;rscr_ 3c;* ramPE is 3 bit field. test PE1 bitrscr2_ a1;* IFUM has all onescall[iDoRamPE], t_ stack;rscr_ 1c;* ramPE is 3 bit field. test PE2 bitrscr2_ a0;* IFUM has all zerosiRamPeL2:* testing PE2 bitcall[iDoRamPE], t_ stack;rscr_ 1c;* ramPE is 3 bit field. test PE2 bitrscr2_ a1;* IFUM has all onescall[iDoRamPE], t_ stack;branch[iRamPeL];iRamPeLXit:stkp-1;* decrement stack where we kept iAddrset[wantExceptionsResched, OR[exceptions.Resched3!, exceptions.Resched2!, exceptions.Resched1!,exceptions.Resched0!]];t _ (and[wantExceptionsResched,177400]C);t _ t or (and[wantExceptionsResched, 377]C);exceptionsMask _ t;call[resetIfu];call[iPat16];iRamPePatL:call[nextPat16];skpif[ALU#0];branch[iRamPeXit];noop;* for placementcall[getPat16], stkp+1;call[getPat16], stack&+1 _ t;stack&+1_ t and (NOT[ifu.peMask!]C);* push stack again, keep iAddr at topcall[setIRamPeJret];call[iIAddr];iRamPeAddrL:call[nextIaddr];branch[iRamPeAddrXit, ALU=0];stack_t;* TOS = iaddr, TOS-1 = rh, TOS-2 = LHcall[resetIfu];t _ (stack) or (mos.ifuCmmd);* set instruction set from current addressmos _ t;*Set reschedNow and write current pattern into new IfuM locationff256[103], stkp-2;* terrible hack to get reschedNowt _ stack&+1;rscr _ t;t _ stack&+1;!gp) :rN bAq2 a _p@^q@]K#@Z+$@Y + XUp+q@W@T+$@S_ +@R"@O+$@Ni + M,p+q@K@Is+$@H6 +@F@D}+$@C@ + Bp+q@@@>J+$@= +@;@9T 8p @6q+% 3 _ 1@0)@/h,@.*@,@*r )4p @'q@& @%|@#+@!@ @H$+%@ @ Rp @q@@+%@\@+*@ f@@ +!@ @ p@ 3  @]Ifu3c.mcJune 21, 1981 1:21 PM%8rscr2 _ t;mc[ifu.notTypeMask, not[or[b10!,b11!]]];rscr2_ (rscr2)AND (ifu.notTypeMask);* keep Pause and Jump logically true.call[putIfuWd], t _ stack;* rscr = lh, rscr2 = rh, t = address*call setIUsingInstrSet so that putting bytes in memory works properly, then load "byte 0" withcurrent opcode (ifum address).t _ ldf[stack, 2, 10];* isolate "instruction set bitscall[setIUsingInstrSet];t _ stack;* make memByte[0] point to current ifucall[putCDbyte], rscr_ A0;* addressiRamPEsetPcF:PcF _ r0;* now begin ifu at location 0call[longWait], t_30c;* a few noops for pipe to fillIfuJump[0];iRamPeCont:memBase _ 0s;RBASE _ rbase[defaultRegion];t _ (rscr) and (dispatchLocBaseMask);t # (reschedBaseLocC);skpif[ALU=0];iRamPEDispatchErr:* we should go to resched only. Any othererror;* dispatch is an error. We went to "rscr".branch[iRamPeAddrL];* move stack down (below address), try next addressiRamPeAddrXit:* try next patternbranch[iRamPePatL], stkp-3;* pop stack since pattern loop pushes it.iRamPeXit:t _ a0;exceptionsMask _ t;call[enableConditionalTask];returnP[];setIRamPeJret:pushReturn[];call[sirpe2];t _ link;klink _ t;returnP[];sirpe2:coreturn;branch[iRamPeCont];!gp) :rN@bAq apq@_$+%@^+$ \_ Z@XU+@W@U +&@T+ S_p @R"q+@P+@O Nip @M,q @K@J%@Is@H6 Fp+q)@E+*@C@+3 @p +q@?+) = p @;q@:@9T@8 5p @4^q @3 @1@0 @/h .*p@,q@+ *OB-=Ifu3c.mcJune 21, 1981 1:21 PM%9* June 20, 1981 2:36 PM% iDoRamPEThis subroutine executes an IfuJump that SHOULD get a ramPE.Enter: rscr=bits for ifuRam PE field in IfuMemoryrscr2= background value for IFUM wordt= IFUM address we will testAlways write IFUM so that the pause bit is logically true (0)%iDoRamPE: subroutine;pushReturn[];stack+1_ t;* SAVE: stack+1=ifuM addressrscr3_ rscr;* rscr3= bits for IFUM PE fieldrscr4_ rscr2;* rscr4= background value for IFUM wordcall[resetIfu];t _ (stack) or (mos.ifuCmmd);* set instruction set from current addressmos _ t;*Set reschedNow and write current pattern into new IfuM locationff256[103];* terrible hack to get reschedNowrscr_rscr4;call[putIfuLH], t_stack;t_ DpF[rscr3, 3, ifu.pe2Shift];* position bits for perscr4_ (rscr4) AND (NOT[ifu.peMask!]C);rscr_ (rscr4) OR (t);rscr_ (rscr) and (ifu.notTypeMask);* mask-out to make pause, jump truecall[putIfuRH], t_stack;*call setIUsingInstrSet so that putting bytes in memory works properly, then load "byte 0" withcurrent opcode (ifum address).t _ ldf[stack, 2, 10];* isolate "instruction set bitscall[setIUsingInstrSet];t _ stack;* make memByte[0] point to current ifurscr_ t;* addresscall[putCDbyte], t_ a0;PcF _ r0;* now begin ifu at location 0call[longWait], t_30c;* a few noops for pipe to fillbranch[iSetDoRamPEcont];iDoRamPEJ:IfuJump[0];iDoRamPeCont:memBase _ 0s;RBASE _ rbase[defaultRegion];t _ (rscr) and (dispatchLocBaseMask);t # (ramPeBaseLocC);skpif[ALU=0];iDoRamPEDispatchErr:* we should go to ramPe only. Any othererror;* dispatch is an error. We went to "rscr".* "stack" contains IFUM address that failed to generate ram pe.* rscr3 contains background value for IFUM word* rscr4 contains bits for ifuRam PE field in IfuMemory. Expect that these bits are set* such that only one of the three bytes in the memory should generate a parity error.* Eg., if rscr4=40000C then one of the bits associated w/ ifu.pe0 is bad* IF rscr4= 3 one of the bits w/ ifu.pe0 is bad (the background value of IFUM is adjusted* so that all non-PE bits in IFUM have same value and the test changes the PE bits.pReturnP[];iSetDoRamPEcont: top level;call[iDoRamPeSetup];klink_link, branch[iDoRamPEJ];iDoRamPeSetup: subroutine;coreturn;branch[iDoRamPECont];!gp) :rN bAq a _< ]K2\%ZY= XU Wpq U T +S_ +R" +'PO+*Ni K@J +!H6 FD}+C@'B@#+#? = _ ;9T+86 +&5+4^1+0+/h .*p ,q +p *rq )4'%&%| $>p+q'#+* !? / HW  U H Y RS \pq  p q f) @ZCIfu3c.mcJune 21, 1981 1:21 PM%10* May 13, 1979 4:11 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuChaosTest generates and executes randomly constructed opcodes from randomly chosen memory locations. Thetest uses tow phases. The first phase involves writing the randomly generated opcode into IFUM andwriting the value of Alpha and Beta into storage. The second phase of the test involves executing andcheckning the ocode.The first phase uses random numbers to choose these characteristics of the opcode:Location of the opcode in storageLocation of the instruction in IFUMThe following characteristics of the instruction:NX or nonePacked alpha or notSign extension or notInstruction lengthInstruction typeIM destination addressRBase and MemBaseThe test always computes proper parity.The test always uses the same IM target addressThe first phases leaves a record of how it constructed the opcode for use by the second phase.The second (checking) phase assures validity of the following:IM target address (as well as it can)PcX_ID sequenceRBaseMbase%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++!gp) :rN bAq a?+f_p ^qd ]Kc \f Z YRXU!W#U1T S_R"PONiM,K'J/Is^ H6>F%ED} C@B ??r >'E3)Ifu3c.mcJune 21, 1981 1:21 PM%11* February 1, 1980 8:04 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuChaos: PROCEDURE =BEGIN-- Main LoopFOR testX IN ChaosTestRange DO-- execute a bunch of testsopCodeRecord _ makeIfuOpcodeRecord[];ifuChaosPhase1[opCodeRecord];-- initialize everything for an opcodesetIfuPc[opCodeRecord.ifuPc];ifuChaosPhase2[opCodeRecord];-- execute and test the opcodeENDLOOP;END;ifuChaosPhase1: PROCEDURE RETURNS [rec: ifuOpcodeRecord] =BEGIN-- Initialization CodeputCDbyte[rec.ifuPc, rec.ifuOpcode];-- write the opcode, alpha and beta intoputCDbyte[rec.ifuPc+1, rec.ifuAlpha];-- storage.putCDbyte[rec.ifuPc+2, rec.ifuBeta];resetIfu[];putIfuWd[rec.ifuOpcode, rec.instrHi, rec.instrLow];-- write opcode into IfuMemresetIfu[];END;ifuChaosPhase2: PROCEDURE [rec: ifuOpcodeRecord] =BEGIN-- Checking CodesetIfuReturnLink[@phase2Return];count _ 25;phase2Loop:IfuJump[];phase2Return:IF (count = 0) THEN SIGNAL TooManyNotReadies[];IF (cameFrom # opAt15) THEN BEGINIF (cameFrom # notReady) THENSIGNAL BadDispatchLoc[cameFrom];END;ELSE BEGINcount _ count-1;goto[phase2Loop];END;END;-- We get here when the test believes the opcode had dispatched correctly.memBaseAndRbase _ POINTERS[];-- machine instruction rtns memBase,,RbaseexpectMemBaseAndRbase _ getExpectedMemAndRbase[];IF getPcX[] # (rec.ifuPc) THEN SIGNAL badPcX[];IF memBaseAndRbase # expectMemBaseAndRbase THENSIGNAL badPointers[memBaseAndRbase, expectMemBaseAndRbase];FOR i _ 1, i+1 UNTIL i=6 DOexpectVal _ getExpectedID[rec];IF ifuDataCount # (expectedIfuDataCount[]) THEN SIGNAL BadIfuDataCount;IF expectVal # (gotValue _ getID[]) THEN SIGNAL BadID[i, expectVal, gotVal];ENDLOOP;END;%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++!gp) :rN bAq a? _pq ^ ]K&\%Z)z&YXU)zWU Tpq+S_P$)z(O%+ Ni$K J33fIs F Epq#D}C@B ?p >Jq = p ;q/:!9T$865 4^3 10/hJ.*$*,1+/*r/)4;'&%|G$>L#! ? %4HIfu3c.mcJune 21, 1981 1:21 PM%12* June 21, 1981 1:20 PMifuChaos: subroutine;pushReturn[];call[initIfuChaosX];ifuChaosL:call[nextIfuChaosX];skpif[ALU#0];branch[afterIfuChaos];noop;* for placementmemBase _ 0s;* undo the effects of any previousmemBX _ 0s;* ifuJump.call[makeIfuOpcodeRecord];call[ifuChaosPhase1];* initialize the Ifu memory, storage.ifuChaosSetPc:call[enableConditionalTask];call[getIfuPc];PcF _ t;t _ 25C;cnt _ t;* this controls number of "not readies" before anerrorcall[setIfuChaosRet];* set KLINKifuChaosPhase2Cont:IfuJump[];ifuChaosPhase2Ret:(rscr) # (opAt15);skpif[ALU#0];branch[ifuChaosPhase2Chk];noop;* for placementcall[getIfuNotReadyLoc];t # (rscr);skpif[ALU=0];ifuChaosDispatchErr:error;* went to unexpected dispatch location.loopUntil[CNT=0&-1, ifuChaosPhase2Cont];ifuChaosPhase2Chk:stkp+1;* get the value of POINTERS thatcall[getIfuRbase], rscr _ stack;* afterDispatch has saved.rscr _ (rscr) and (17C);* isolate rbase from POINTERSt # (rscr);* NOTE: stack= value of POINTERS saved byskpif[ALU=0];* afterdispatch. Don't forget to decrement stkp!ifuChaosRBaseErr:* t = expected rbase, rscr = real rbaseerror;call[getIfuPc];rscr _ not(PcX');(rscr) # t;skpif[ALU=0];ifuChaosPcXErr:* rscr = PcX, t = expected value for PcXerror;* check MemBasecall[getIfuMbase];rscr _ stack&-1;* scarf POINTERS and decrement StkP. See above.rscr _ ldf[rscr, 5, 10];* isolate membase from POINTERSt # (rscr);skpif[ALU=0];ifuChaosMBaseErr:* t = expected rbase, rscr = real rbaseerror;RBASE _ rbase[defaultRegion];* Heretofor we've avoided depending uponcall[setMBase], t _ r0;* these values.cnt _ 6s;!gp) :rN bAq _pq ^ ]K ZpqYXU WU+S_ +"R" + ONi+% Kp JqIsH6FE+1 D}C@+ @p?q = p;q: 9T8+65 4^ 3 p1q+'/h( ,p+q+*r+)4+' +)& +1 %|p+q'$>! H  p+q( +0\+  p+q'f +( + 3H A] Ifu3c.mcJune 21, 1981 1:21 PM%13ifuChaosIDL:noop;call[getExpectedID];rscr _ ID;PD _ (rscr) # t;skpif[ALU=0];* t = expected ID, rscr = actual IDifuChaosIDErr:* (cnt-5) = number of IDs performederror;* ifuChaosOpcode = the opcodeloopUntil[CNT=0&-1, ifuChaosIDL];* ifuChaosPc = memory locationbranch[ifuChaosL];afterIfuChaos:call[disableConditionalTask];returnP[];setIfuChaosRet:pushReturn[];call[sicR2];t _ link;klink _ t;returnP[];sicR2:coreturn;branch[ifuChaosPhase2Ret];!gp) :rN bA aq_^ ]K\ +# Zp +q#Y+XU!+U S_p R"qP NipM,q K JIs H6 FpEqD} C7m$sIfu3c.mcJune 21, 1981 1:21 PM%14* September 18, 1979 11:13 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuBrkInsTestTest the BrkIns register as it would be used for implementing breakpoints:Load BrkInsSet PcFGExecute an IfuJumpIf BrkIns is working properly, we'll execute the opcode loaded in BrkIns, otherwise we'll execute theopcode pointed to by PcFG.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuBrkInsTest:pushReturn[];call[initIfuCache];call[enableConditionalTask];noop;* for placement.call[resetIfu];call[setIUsingInstrSet], t _ 3c;call[ifuSetInstrSet], t _ 3c;call[putCDbyteAddr], t _ A0;* we'll set PcFG to zeronoop;* for placement.call[appendHalts];call[appendHalts];* lots of halt opcodes which we should never execute!call[setIfuBrkInsRet1];ifuBrkInsScopeL:ifuReset;t _ 40c;cnt _ t;loopUntil[CNT=0&-1, .];ifuReset;call[justReturn];* for patching into call[scopeTrigger],t _ lshift[opNoop!, 10]C;* it's needed. Remember, BrkIns loads fromtaskingOff;* left half of BmuxPcF _ r0;BrkIns _ t;taskingOn;cnt _ 17s;ifuBrkInsL1:IfuJump[0];ifuBrkInsCont1:(rscr) # (is3NotReadyLocC);branch[ifuBrkInsChk, ALU#0];noop;* for placementloopUntil[CNT=0&-1, ifuBrkInsL1];* got not ready. try againifuBrkInsNotReadyErr1:* always went to not readyerror;* this should not have happenedifuBrkInsChk:(rscr) # (opAt15);* see if we went where we expectedskpif[ALU=0];ifuBrkInsJmpErr1:* expected to execute opNoop which woulderror;* have taken us to opAt15* now try it again, except flush the munch from the cacheFlush _ 0s;call[justReturn];* for patching into call[scopeTrigger],t _ lshift[opNoop!, 10]C;* it's needed. Remember, BrkIns loads fromtaskingOff;* left half of BmuxPcF _ r0;BrkIns _ t;taskingOn;t _ 100c;cnt _ t;call[setIfuBrkInsRet2];loopUntil[CNT=0&-1, .];* now wait right here for a long whileIfuJump[0];ifuBrkInsCont2:(rscr) # (opAt15);* should have gone directly to opAt15skpif[ALU=0];ifuBrkInstJumpErr2:error;* went to "rscr" rather than opAt15!gp) :rN bAq aB)_p ^qJ]K \Z Ye XU WB Up Tq S_R"P+ONiM,K+J+IsH6+5F EpD}qC@B@?>J+'= +*; +:9T 8 6 5p 4^q 1p0q/h.*+,!+ +p+q*r+ )4p 'q+"& %|p+q($>+ 9H  +'+* +R  \+& fp)q+% p pq+# D]@Ifu3c.mcJune 21, 1981 1:21 PM%15call[disableConditionalTask];returnP[];setIfuBrkInsRet1:pushReturn[];call[setIfuBrkIns1];t _ link;klink _ t;returnP[];setIfuBrkIns1:coreturn;branch[ifuBrkInsCont1];setIfuBrkInsRet2:pushReturn[];call[setIfuBrkIns2];t _ link;klink _ t;returnP[];setIfuBrkIns2:coreturn;branch[ifuBrkInsCont2];top level;!gp) :rNbAqa ^p]Kq \ZY XU Wp UqT R"pPq ONiM, K Jp IsqH6E L DZ#fifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%1%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Table of ContentsOrganized by Occurence of subroutine in this ListingSubroutineFunction+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuChaosPhase1:First half of current chaos testmakeIfuOpcodeRecord:Creates the data for the current opcodefixIfuInstr:Modify ifuInstrRH so that it is legal.makeExpectedID:Returns currently expected value of IfuDatagetIfuIDsequence:Returns the encoding for expected _ID sequenceinitIfuChaosX:initi ifu chaos index variablenextIfuChaosX:return next ifu chaos index variable (ALU=0 => done)getIfuOpcode:return current value of ifuOpcodegetIfuAlpha:return current value of ifuAlphagetIfuBeta:return current value of ifuBetagetIfuInstrLH:return current value of ifuInstrLHgetIfuInstrRH:return current value of ifuInstrRHgetIfuInstrIL:return value of current ifuInstr's ILgetIfuRBasereturn value of current ifuInstr's rbasegetIfuMbasereturn value of current ifuInstr's membasesetIfuILfield:modify IL field of an ifu instr in rscr, new value in tsetIfuTypefield:modify type field of an ifu instr in rscr; new val in t%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%September 17, 1979 11:20 AMFix bug in SetIfuTypeField -- apparently a lost fix, I remember doing this once before.July 2, 1979 5:44 PMFix seqTable so that 1 byte opcodes w/ packed alpha And encoded constants return IL instead of NX,IL.July 1, 1979 1:24 PMFix more bugs in getExpectedID -- beta is never sign extended.July 1, 1979 12:55 PMFix some bugs in getExpectedID -- called getIfuInstrLH instead of getIfuInstrRH when trying toaccess sign extension bit.June 30, 1979 6:30 PMFix several more bugs in makeIfuSequence.June 30, 1979 5:39 PMChange some labels in makeIfuSequence that still use "getIfu...", fix 2 bugs in computation of theindex --using wrong register and failure to set a register. getExpectedID uses wrong mask to isolatean octal digit, sign extention logic is incorrect on IDisNX, IDisAlpha, IDisBeta.June 29, 1979 5:19 PMChange makeIfuOpcodeRecord's call to getIfuSequence (no longer exists)into call onmakeIfuSequence.June 29, 1979 5:04 PMRename getIfuSequence to makeIfuSequence (since it always reconstructs the ifuSequence valuerather than returning the current one), and fix a bug in computing whether or not 10B should get or'dinto the table index -- skip/sex bug. Change getExpectedID to access ifuSequence directly rather thancalling getIfuSequence.June 29, 1979 4:18 PMAdd ;s to end of data statements that define the seqTable -- this clobbered the first instructionofgetExpectedId.June 29, 1979 3:31 PMChange incorrect call to ifuSetInstrSet in ifuChaosPhase1 to setIUsingInstrSet. Fix small bugs ingetIfuRbase, getIfuMbase.June 29, 1979 11:56 AMifuChaosPhase1 called getIfuPc where it should have called getIfuOpcode.June 29, 1979 10:59 AMFix bug in makeIfuOpcodeRecord -- neglected to call getIfuSequence and setifusequence.June 29, 1979 10:03 AMFix bugs associated with fixIfuInstr. In particular, micro does not complain about the construct,"t _ not[ifu.ilMask];" It generates an instruction of "PD_3c" which is completely wrong. The propersyntax (I wrote it wrong) is "t _ not[ifu.ilMask!]C;".June 24, 1979 5:54 PMAdd get(IfuRBase, Mbase, MBx).June 24, 1979 4:28 PMRemove all uses of dpf that deposit into rm or t!June 19, 1979 10:02 AMFix fixIfuInstr and makeIfuOpcodeRecord--used hi true ifadm in mior and used wrong register inZgp)?&N bAqB(`ap_4^q "  ]K?\p" qZp" q'Yp " q&XUp" q+Wp" q.Up " qTp " q4S_p " q!R"p " qPp " qOp " q"Mp " q"LXp " q%Kp " q(Ip " q*Hp " q7Gbp" q7 F$B Bl A.1?W >1=vb <8 :19> 817B_ 6 413) 2L11b /e .Q -V1,R * )1(`\ '#e %f $ #j1"-a  1tb 7 1H ~1AJ  1b Ke  6 1 U1 1 1 ^ yE3]SifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%2fii.June 17, 1979 6:02 PMChange location of sequence table to accommodate changes in postamble that accommodate ifuentrypoint locations.Fix placement problems in fixInstr, getIfuSequence, readSeqTableJune 5, 1979 10:23 AMRemove placement errors, add new procedures.June 1, 1979 6:14 PMRemove makeifuopcoderecord from ifuchaosphase1 so that an infinit loop can be constructed when aparticular opcode goes astray.May 22, 1979 11:55 AMAdd ifuChaosPhase1, various other subroutines, makeIfuOpcodeRecord's microcode.May 14, 1979 9:15 PMAdd makeIfuOpcodeRecord, getIfuIDsequenceMay 2, 1979 10:53 AMConstruct this file and begin to write Mesa version of getExectedID.%Zgp)?&N bAq a1_Z ^1]K@ \1Z, Y1XU` W U1TO S_1R") P1OD Ni M CWifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%3* June 29, 1979 3:32 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuChaosPhase1This subroutine uses the data record created by makeIfuOpcodeRecord to initialize all the raw dataassociated with the current test. It uses that data to write into IFUM, and storage.The "opcode record", which is really a dedicated RM region, contains the following information:ifuPcByte address in storage for the test opcodeifuAlphaFirst data byte (may not be used by instruction)ifuBetaSecond data byte (may not be used by instruction)ifuOpcodeThe value of the opcode (ie., address, including instruction set bits, inthe Ifu memory).%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuChaosPhase1:pushReturn[];%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Write opcode, alpha, beta into storage%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++call[getIfuOpcode];* write opcode; begin by setting currentt _ ldf[t, 2, 10];* instruction set indicatorcall[setIUsingInstrSet];call[getIfuOpcode];call[getIfuPc], rscr _ t;call[putCDbyte], stack+1 _ t;* push addr of opcode onto stackcall[getIfuAlpha];* write Alpharscr _ t;call[putCDbyte], t _ (stack)+1;call[getIfuBeta];* write Betarscr _ t;call[putCDbyte], t _ (stack&-1) + (2c);%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Write instruction into IfuMem%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++call[resetIfu];call[getIfuInstrLH];call[getIfuInstrRH], rscr _ t;call[getIfuOpcode], rscr2 _ t;call[putIfuWd];call[resetIfu];returnP[];Zgp)?&N bAq aB)b_p ^qb ]KU \_Z+Y0XU1WIUT! S_B Pp q1O M,B!RKp& JqBIs+(H6+FED}C@+@+ ?>J;+ :9T' 6B$X5p 4^qB3 10/h.*,+ | *OB=ifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%4* June 29, 1979 5:20 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++makeIfuOpcodeRecordCreate all the data associated with the new opcode. This includes constructing the high and low wordsfor the Ifu Memory, choosing the opcode value and instruction set, choosing alpha and beta, andassuring that the instruction is legal (no 3 byte jumps, no instructions of type (jump and pause).makeIfuOpcodeRecord: PROCEDURE RETURNS [rec: IfuOpcodeRecord] =BEGIN OPEN rec;ifuPc _ getRandom[];ifuAlpha _ getRandom[] and 377B;ifuBeta _ getRandom[] and 377B;ifuOpcode _ getRandom[] and 1777B;ifuInstrHi _ getRandom[] and ignoreIfAdMmask;ifuInstrLH _ getRandom[] and (ignoreParity);[ifuInstrHi, ifuInstrLH] _ fixIfuInstr[ifuInstrHi, ifuInstrLH];ifusequence _ getIfusequence[ifuInstrHi, ifuInstrLH];END;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++makeIfuOpcodeRecord: subroutine;pushReturn[];getRandom[];* 16-bit byte pcifuPc _ t;getRandom[];* Alpha and BetaRBase _ rbase[ifuBeta];ifuBeta _ ldf[t, 10, 0];* extract right byteifuAlpha _ ldf[t, 10, 10];* extract left byteRBASE _ rbase[defaultRegion];getRandom[];* opcode, including instruction set bitst _ t and (1777C);ifuOpcode _ t;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++The instruction, as it appears in the ifu memory, consists of two parts, the left and right halves.The left half contains the packed alpha bit (selected randomly) and the IM target address that isalways chosen to be the IM address, opAt15. The right half contains the parity bits which this codemasks out. Correct parity gets constructed when the words are written into the Ifu memory. Thesubroutine, fixIfuInstr, modifies il and it (length and type) to guarantee that the instruction islegal.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getRandom[];* The actual instruction in Ifu Memoryrscr _ lshift[1, ifu.paShift]C;* isolate packed alphat _ t and (rscr);rscr _ not (15c);* default IfadM = opAt15rscr _ (rscr) and (ifu.adMask);* Remember that Ifad bits are low true.t _ t or (rscr);ifuInstrLH _ t;getRandom[];t _ t and (not[ifu.peMask!]C);* don't set the parity bits in ifuRHifuInstrRH _ t;call[fixIfuInstr];call[makeIfuSequence];ifuSequence _ t;returnP[];Zgp)?&N bAq aB'_p ^qf ]K_ \Wrq Ypq+XUWUTS_"R"-P,O?Ni5M, KB Ispq H6 E +D} B +@?+>J+= : +(9T8 5B 4^c 3 Zr 1+q9 0` /hb .* ,B+ +&*r+)4&+%|+'$># H+$ R  9E3RifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%5* June 29, 1979 10:08 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++fixIfuInstrThis subroutine guarantees that the ifuOpcodeRecord is legal. A randomly chosen instruction maycontain zero length instructions, 3 byte jumps, or instructions that are both of type pause and jump.These are illegal and must not occur.fixIfuInstr: PROCEDURE[hi: IfuHiPart, low:ifuLowPart] RETURNS [newHi: IfuHiPart, newLow: ifuLowPart] =BEGINnewHi _ hi;newLow _ low;IF low.il = 0 THEN newLow.il _ 3;-- zero length instructions are illegalIF (newLow.il = 3) AND (newLow.type = jump) THEN newLow.il _ 2;IF (newLow.type=jumpAndPause) THEN newLow.type _ jump;END;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++fixIfuInstr:pushReturn[];call[getIfuInstrRH];call[getIfuIL], rscr _ t;* save ifuInstrRH in rscrt _ t # (0c);* see if IL = 0skpif[ALU=0];branch[fixInstr2];*If so, reset it to 3call[setIfuILfield], t _ 3c;* use rscr = instr, t = new ilIfuInstrRH _ t;fixInstr2:call[getIfuIL];PD _ t # (3C);skpif[ALU=0];* (IL bits low true) IF IL=3 ANDbranch[fixInstr3];* (IL is not 3)t _ ldf[rscr, ifu.jumpSize, ifu.jumpShift];PD _ t;* jump is low truebranch[fixInstr3, ALU#0], t _ 2c;* ...IF JUMP THEN IL _ 2call[setIfuILfield];* use rscr = instr, t = new ilIfuInstrRH _ t;fixInstr3:t _ ldf[rscr, ifu.typeSize, ifu.typeShift];PD _ t;* IF type = (JUMP AND PAUSE)branch[fixInstr4, ALU=0], t _ rscr;fixInstrCont:IfuInstrRH _ t;returnP[];top level;fixInstr4:call[setIfuTypefield], t _ (r0)+1;branch[fixInstrCont];Zgp)?&N bAq _B*d^p ]Kq` \e Z% XUp qZWU T S_!)z'R"?P6O NiB M,p Kq JIs+F +E D}+C@+B ?p >Jq= ; +:+8+6+5!+4^+3  0p /hq+.*+,# +p *rq)4 ' &p %|q"$> !E3FkifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%6* July 2, 1979 5:44 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++makeIfuSequenceReturn a sequence of values (each value is an octal digit -- 3 bits) that describes the sequence ofdata that the Ifu delivers in response to "_ID". The rightmost octal digit encodes the type of thecurrent IfuData. As the test performs _IDs, the routine that returns the expected IfuData and rightshifts the sequence to keep in synch with the Ifu. Zero encodes "IL", so an unlimited number of _IDscan be properly simulated.The table, sequenceTable, which is addressed by information about the current opcode, contains asequence for all the relevant different possible sequences that aren't JUMP instructions. Rememberthat all jump instructions return ID = IL. The indeces for the table consist of the concatenation ofthe following bits: . Thus there 20B entries that range [0..17B]. The bitnx=17 means that there's no encoded constant, pAlpha means packed alpha is true, and IL0, IL1 are theinstruction length bits.Here is a table that interprets the octal digits in a sequence:0 => IL1 => nx2 => alpha3 => alpha1 (packed alpha -- left side)4 = > alpha2 (packed alpha -- right side)5 => beta6,7 => ERRORmakeIfuSequence: PROCEDURE[hi:hiInstrPart, low: LowInstrPart] RETURNS[seq: ifuSequence] =BEGINsequenceTable = ARRAY[0..17B] OF CARDINAL _[-- x refers to index (octal) in the table. The four bits that-- address the entry are shown before the sequence. Illegal instructions-- imply zero length instructions.77777B,-- x=0,<0,0,0,0>illegal01B,-- x=1,<0,0,0,il1>IL, nx021B,-- x=2,<0,0,il0,0>IL, alpha, nx0521B,-- x=3,<0,0,il0,il1>IL, beta, alpha, nx77777B,-- x=4,<0,pA,0,0>illegal00B,-- x=5,<0,pA,0,il1>IL USED to be 01, IL nx0431B,-- x=6,<0,pA,il0,0>IL, pAlpha2, pAlpha1, nx05431B,-- x=7,<0,pA,il0,il1>IL, beta, pAlpha2, pAlpha1, nx77777B,-- x=10,illegal00B,-- x=11,IL02B,-- x=12,IL, alpha052B,-- x=13,IL, beta, alpha77777B,-- x=14,illegal00B,--x=15,IL043B,-- x=16,IL, alpha2, alpha10543B,-- x=17,IL, beta, alpha2, alpha1];IF low.type=jump THEN RETURN[seq_0];IF low.il=0 THEN SIGNAL ZeroLengthInstr[hi, low];x _ IF hi.nx=17=17 THEN 0 ELSE 10B;-- "nx17"x _ x or (IF low.pAlpha THEN 4 ELSE 0);-- "pAlpha"x _ x or (low.il AND 3);-- "IL0IL1"seq _ sequenceTable[x];IF seq = 77777 THEN SIGNAL illegalInstruction[hi, low];RETURN;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++makeIfuSequence:pushReturn[];call[getIfuInstrRH];rscr _ t;* keep IfuInstrRH in T.rscr2 _ ldf[t, ifu.jumpSize, ifu.jumpShift];PD _ rscr2;skpif[ALU#0];branch[makeIfuSeqRet], t _ t-t;* jump instrs' seq = 0noop;* for placement.call[getIfuIL];PD _ t;skpif[alu#0];Zgp)?&N bAq _B) ^p \qc [c ZCd Ye W U p qH Tc Se REd Qe O M?L5JI H|'G?)FD BIpqIA ?+> >=SI<": .9 .8] . 7 .5 .4 .3g .2) .0 ./ ..q .-3 .+ .* .){ .(= .'%$$1#G#." '.  . Q7 B pq e+(,  o+2+   y  VD]_ifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%7makeIfuSeqErr0:* should never see zero length instructionerror;t _ (rscr) and (ifu.nMask);* now construct in rscr2 the index into(t) # (17c);* the table.skpif[ALU=0], rscr2 _ 10c;* assume nx = 17rscr2 _ a0;* no, nx#17, there's an encoded constantcall[getIfuInstrLH];* check for packed alphat _ ldf[t, ifu.paSize, ifu.paShift];PD _ t;skpif[ALU=0];rscr2 _ (rscr2) or (4c);* packed alpha contributes 4B to indexcall[getIfuIL];* IL contributes low 2 bits of index.t _ rscr2 _ (rscr2) or t;call[readseqTable];makeIfuSeqRet:returnP[];%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++readSeqTableActually reads the sequence table given t = index in table.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++set[seqTableLoc, 5000];mc[seqTableLocC, seqTableLoc];readSeqTable:pushReturnAndT[];rscr _ seqTableLocC;t _ (stack) and (17c);t # (stack);skpif[ALU=0], t _ t rsh 1;readSeqTableErr:* called with parameter > 7Berror;t _ (rscr) + t;* this is the word addressbranch[readSeqTableRH, r odd], stack;noop;* for placementcall[getImLh];PD _ t # (7c);readSeqTableChk:skpif[ALU#0];readSeqTableErr2:error;* got '7' which is illegalpReturnP[];readSeqTableRH:* read right half of sequence tabletop level;call[getImRh];branch[readSeqTableChk], PD _ t # (7c);%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++seqTableThe entries in this table must be read left to right in increasing IM address. Ie., seqTable[1] is 01and seqTable[2] is 21.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++data[(seqTable:lh[77777]rh[01],at[seqTableLoc, 0])];data[(lh[21]rh[521],at[seqTableLoc, 1])];data[(lh[77777]rh[00],at[seqTableLoc, 2])];data[(lh[431]rh[5431],at[seqTableLoc, 3])];data[(lh[77777]rh[0],at[seqTableLoc, 4])];data[(lh[2]rh[52],at[seqTableLoc, 5])];data[(lh[77777]rh[0],at[seqTableLoc, 6])];data[(lh[43]rh[543],at[seqTableLoc, 7])];Zgp)?&N bA+q*a^+']K + \+Z +(XU+W$UT S_+&P+%ONi M,p Kq IsB*H6p Fq; EB C@ B ?p >Jq= ;: 9T 8p+q65+4^%3 +1 0 /hp.*q ,p+q+)4 &p+q#%| $> #' B+fHp  qf  B pq`+ `+\`+ `+`+ `+f`+) `+ E3[.ifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%8* July 1, 1979 1:26 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getExpectedIDReturn the currently expected value for "ID". We use the value indicated by the right mostoctal digit in ifuSequence. A side-efect of calling this routine is that the ifuSequencevalue gets right shifted.getExpectedID: PROCEDURE[rec: IfuOpcodeRecord] RETURNS[expect: CARDINAL] =BEGINtype _ rec.ifuSequence AND 3b;rec.ifuSequence _ (rec.ifuSequence rshift 3);expect _ SELECT type FROM0 => rec.ifuInstrLH.il;1 => IF (rec.ifuInstrLH.sign # 0) AND ((rec.ifuInstrLH.nx and 10) # 0)THEN 17776B or rec.ifuInstrLH.nxELSE rec.IfuInstrLow and 17B;2 => IF (rec.ifuInstrLH.sign # 0) AND ( (rec.ifuAlpha and 200B) # 0)THEN 177400B or rec.ifuAlphaELSE rec.ifuAlpha;3 => ifuAlpha AND 17B;4 =>(ifuAlpha rshift 4) AND 17B;5 => rec.ifuBeta;default => SIGNAL illegalIDsequence;END;END;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getExpectedID:pushReturn[];RBASE _ rbase[ifuSequence];t _ ifuSequence, RBASE _ rbase[defaultRegion];rscr _ t and (7c);* isolate current sequence digit, andt _ rsh[t, 3];* replace current sequence with rightcall[putIfuSequence];* shifted versionbdispatch _ rscr;* go compute correct IDbranch[expectedIDis];set[IDisTbl, 4200];expectedIDis:branch[IDisIL],at[IDisTbl, 0];branch[IDisnx],at[IDisTbl, 1];branch[IDisAlpha],at[IDisTbl, 2];branch[IDisAlpha1],at[IDisTbl, 3];branch[IDisAlpha2],at[IDisTbl, 4];branch[IDisBeta],at[IDisTbl, 5];branch[IDisBad],at[IDisTbl, 6];branch[IDisBad],at[IDisTbl, 7];IDisIL:call[getIfuIL];branch[getExpectedIDret];IDisNX:call[getIfuInstrRH];branch[getExpectedIDret], t _ t and (ifu.nMask);* t = sign extended nxIDisAlpha:call[getIfuInstrRH];* isolate signX into rscrrscr _ ldf[t, 1, ifu.signShift];call[getIfuAlpha];* get the value of alphaPD _ rscr;skpif[ALU#0];branch[getExpectedIDret];* signX is not true, so NO sign extentiont and (200C);* see if hi order bit of alpha is set.skpif[ALU=0];t _ t or (177400C);* We must extend the signbranch[getExpectedIDret];IDisAlpha1:call[getIfuAlpha];branch[getExpectedIDret], t _ ldf[t, 4, 4];Zgp)?&N bAq aB)_p ^q[]KY\ Zp q>YXUW-UTS_FR"PpOqDNiM,KJIsH6$FE D}B Bp @q ?>J.= +%; +%:+8+65 4^p 3 q+1+0+/h+.*+,+++*r+ 'p&q%|p q #p!q 00Z  p q++  \+) +& f+) p  pq 3+^ =]0ifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%9IDisAlpha2:call[getIfuAlpha];branch[getExpectedIDret], t _ ldf[t, 4, 0];IDisBeta:call[getIfuBeta];branch[getExpectedIDret];IDisBad:error;* rscr = sequence digit, ifuOpcodeRecord contains current info.getExpectedIDret:returnP[];Zgp)?&N a _q^+ \pZqY WpUqE S_pR"q  P2%J?ifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%10* June 29, 1979 3:33 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++initIfuChaosXnextIfuChaosinitIfuChaosXinitialize ifu chaos loop controlnextIfuChaosXincrement and return next ifuchaos loop value (ALU=0 => no more)getIFUxxxWhere xxx are the pieces of the ifuOpcodeRecordsetIfuILfieldrscr = ifuRH, t = hi true, new value for il. Return t = new ifuRHsetIfuTypeFieldrscr = ifuRH, t = hi true, new value fo type, Return t = new IfuRH.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++initIfuChaosX: subroutine;t _ cm1;return, ifuChaosX _ t;nextIfuChaosX: subroutine;RBASE _ rbase[ifuChaosX];t _ ifuChaosX _ (ifuChaosX)+1, RBASE _ rbase[defaultRegion];t - (ifuChaosEndC);RETURN, t-(ifuChaosEndC);getIfuOpcode: subroutine;RBASE _ rbase[ifuOpcode];return, t _ ifuOpcode, RBASE _ rbase[defaultRegion];getIfuPc: subroutine;RBASE _ rbase[ifuPc];return, t _ ifuPc, RBASE _ rbase[defaultRegion];getIfuAlpha: subroutine;RBASE _ rbase[ifuAlpha];return, t _ ifuAlpha, RBASE _ rbase[defaultRegion];getIfuBeta: subroutine;RBASE _ rbase[ifuBeta];return, t _ ifuBeta, RBASE _ rbase[defaultRegion];getIfuInstrLH: subroutine;RBASE _ rbase[ifuInstrLH];return, t _ ifuInstrLH, RBASE _ rbase[defaultRegion];getIfuInstrRH: subroutine;RBASE _ rbase[ifuInstrRH];return, t _ ifuInstrRH, RBASE _ rbase[defaultRegion];getIfuIL: subroutine;RBASE _ rbase[ifuInstrRH];t _ ldf[ifuInstrRH, ifu.ilSize, ifu.ilShift];t _ not(t), RBASE _ rbase[defaultRegion];* return true sexreturn, t _ t and (3c);getIfuRBase:pushReturn[];call[getIfuInstrRH];rscr2 _ ldf[t, 1, ifu.rbSelShift];PD _ rscr2;skpif[ALU=0], t _ (r0)+1;* (low true) 0 ==> rbase should be 1t _ a0;* (low true) 1 ==> rbase should be 0returnP[];getIfuMBase:pushReturn[];call[getIfuInstrRH];rscr _ ldf[t, 2, ifu.memBLow2Shift];t _ ldf[t, 1, ifu.memBK34Shift];PD _ t;skpif[ALU=0], t _ rscr;t _ t or (34C);* add 2 bitsreturnP[];putIfuSequence:return, IfuSequence _ t;Zgp)?&N bAq aB)_p *^ ]K q! \p q@ Zpq/ Yp qB XUpqC WB Up q 1T1S_ Pp q 1O1Ni<1M,1K Isp q 1H61F4 D}pq 1C@1B0 ?p q 1>J1= 3 :p q 19T182 5p q 14^13 5 0p q 1/h1.*5 +pq @*r@)4-@')+@& $>p @#q @!@ "@H @ +$@+$@ p @q @@\$@@@@f+ @) p@ pq : ]ifuChaosSubrs.mcSeptember 17, 1979 11:20 AM%11setIfuILfield:pushReturnAndT[];% enter w/ t = new IL bits, rt. justified,and rscr = current value of ifuRH. Return T = new value for ifuRH. Original value in T istreated as if it were high true! We invert the bits before modifying the value found in rscr. Thus,this routine stores low true values into IL. Return with rscr unmodified.%stack _ not(stack);stack _ (stack) and (ifu.ilMask);* force into low true valuet _ not[ifu.ilMask!]C;*remove current IL bitst _ lcy[t,t, ifu.ILshift];rscr _ t and (rscr);stack _ lsh[stack, ifu.ilShift];* position new il bitst _ t or (stack&-1);* add new bits & decrement stackreturnP[];setIfuTypefield:pushReturnAndT[];% enter w/ t = new type bits, rt. justified,and rscr = current value of ifuRH. Return T = new value for ifuRH. Original value in T is treated asif it were high true! We invert the bits before modifying the value found in rscr. Thus, thisroutine stores low true values into type. Return with rscr unmodified.%stack _ not(stack);stack _ (stack) and (ifu.typeMask);* force into low true value.t _ not[ifu.typeMask!]C;*remove current type bitst _ lcy[t,t, ifu.typeShift];rscr _ t and (rscr);t _ lsh[stack&-1, ifu.typeShift];* position new type bitst _ t or (rscr);* add new bits & decrement stackreturnP[];Zgp)?&N bA @aq+*@_[ ^e ]KJ \@Y@XU!+@U+@T@S_@P+@O+@Ni Kp@Jq+, Isf H6_ FG E@C@@B#+@?+@>J@= @:!+@9T+@8 " 6E31UMODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%1TITLE[ifuDefs];%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++June 17, 1981 3:30 PMAdd opSign3 for miscEffects test.May 28, 1981 2:54 PMChange Bmux to BmuxRM to eliminate midas unhappiness.February 1, 1980 5:48 PMAdd patterns 5 &6 for the pattern generator constants.October 10, 1979 3:32 PMAdd lastEventBOctober 9, 1979 10:42 AMAdd lastEventAOctober 8, 1979 7:14 PMAdd ctrFlag.September 27, 1979 5:37 PMAdd ctrLo, ctrHi, beginHi, beginLoJuly 2, 1979 11:53 PMdefine exceptions.*, RM locations for exception (ifu exception) handling.June 24, 1979 5:41 PMAdd definition for ifu.typeMask.June 20, 1979 8:14 AMAdd new RM definitions (in defaultRbase) for ifu random address/data testJune 19, 1979 8:00 AMAdd new 16 bit pattern constant.June 18, 1979 9:35 AMAdd constants to define"base" dispatch locations.June 17, 1979 4:24 PMMove old "opIfad10" to "opIfad22" because of FGParity3 conflictJune 15, 1979 4:21 PMAdd mos.ifuCmmdJune 7, 1979 5:34 PMSet defaultFlagsP to flags.conditionalP.June 5, 1979 12:41 PMUpdate ifLength macro to use ILlength, ILMask, ILsize symbols.June 5, 1979 11:29 AMAdd rbsel and membk34 definitions for ifuchaos.June 1, 1979 6:32 PMMore IfuChaos glitches.May 30, 1979 5:48 PMGlitches to accommodate ifuChaos.May 30, 1979 11:00 AMAdd MemoryOK for initMem, add new pattern limit for pat16.May 23, 1979 10:42 AMAdd rm definitions for ifu chaos.May 1, 1979 6:58 PMFix ifu.instrSet* for difference between 'geting' and 'seting'.May 1, 1979 4:58 PMAdd ifu.InstrSetSize, ifu.InstrSetShift, ifu.InstrSetMask.April 26, 1979 8:54 AMAdd iUsingInstrSet, pat8X.April 25, 1979 12:53 PMAdd fastexit, fastfetch, faststore definitions.April 24, 1979 3:47 PMRemove dispatchOffset=r01, change iAddrX to r01.April 23, 1979 9:02 AMMove opcode definitions (byte values) from ifu3 to here.April 19, 1979 11:01 AMIncrement lastTestCountC, create composeIfuWd macro.April 5, 1979 12:05 AMAdd rm & constants to control test execution.March 2, 1979 9:12 AMAdd constants for exception conditions.February 15, 1979 9:00 AMChange ifum definition macros to save IM space.January 26, 1979 5:26 PMMake ifum macros call subroutines rather than do all the work in-line.January 22, 1979 8:27 PMConstruct IfAdHi, ifAdLow to cope with ifadm values that aren't legal ff constants.January 22, 1979 9:33 AMMake b0 the default trigger valueJanuary 17, 1979 2:50 PMpat16End2C, instruction set parameter for endIfuWdgp->zN bAq a? _1^! ]K1\5 Z1Y6 XU1W U1T S_1R" P1O" Ni1M,I K1J Is1H6I F1E D}1C@1 B@? ?>J = ;( :9T> 86/ 54^ 3 1! 0/h: .*,! +*r? )4': &%| $>#/ ! 0 H 8 4 R- ' \/ F f)S  ! p 32 ;]"MODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%2%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++gp->zN bAq?l ^*S <MODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%3* October 10, 1979 3:34 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++IFU RegisterDeclarationsIfu Loop control constants%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++RMRegion[ifuSubrsRM];rv[iLink0,0];rv[iLink1, 0];rv[iSubrScr, 0];rv[triggerCount, 0];rv[triggerValue, b15];rv[triggerZero, 0];rv[clockCount, 0];rv[currentCDbyte,0];rv[iTestX, 0];* current test indexrv[iTestCountX, 0];* current iteration count for current testrv[iCurrentTestLoc, 0];rv[iUsingInstrSet, 0];rv[pat8X, 0];rv[ifuChaosX, 0];rv[memoryOK, 0];RMRegion[ifuChaosRM];rv[ifuPc, 0];rv[ifuAlpha, 0];rv[ifuBeta, 0];rv[ifuOpcode, 0];rv[ifuInstrLH, 0];rv[ifuInstrRH, 0];rv[ifuSequence, 0];* The exception (Kfault, FGPe, Resched, RamPE) handling code uses these locations.rv[exceptionsMask, 0];rv[exceptionBit, 0];rv[exceptionPointers, 0];* Counter valuesrv[ctrBeginLo, 0];rv[ctrBeginHi, 0];rv[ctrElapsedHi, 0];rv[ctrElapsedLo, 0];rv[lastEventA, 0];rv[lastEventB, 0];knowRbase[defaultRegion];rm[expectedDispatch, IP[r10]];rm[pat16, IP[rhigh1]];rm[bmuxRM, IP[rhigh1]]; rm[iAddr1, IP[rhigh1]];rm[pat16X, IP[rm1]];rm[FGbits, IP[rm1]];rm[iAddr2, IP[rm1]];rm[IAddrX, IP[r01]];rm[value1left, IP[r01]];rm[value1right, IP[rscr3]];rm[ctrLo, IP[rscr3]];rm[value2left, IP[rscr4]];rm[ctrHi, IP[rscr4]];rm[value2right, IP[stackPAddr]];rm[ctrFlag, IP[stackPAddr]];br[br0,0];mc[IfuEndAddrC, 2000];* last ifu address + 1mc[pat16End1C, 20];* IN [0..20)mc[pat16End2C, 40];* IN [0..40)mc[pat16End3C, 60];* IN [0..60)mc[pat16End4C, 200];* IN [0..100)mc[pat16End5C, 201];* IN [0..101)mc[pat16End6C, 202];* IN [0..102)mc[pat16EndAllC, 202];* IN [0..102)mc[lastTestC, 4];* IN [0..4)mc[lastTestCountC, 1000];* IN [0..1000)mc[ifuChaosEndC, 10000];* IN [0..10000)sp[defaultFlagsP, flags.conditionalP];* conditional task and hold sim -- used by postamble.gp->zN bAq a?&_p%Z^ \q? Y Xpq Wpq VDpq Up q Sp q Rp q QNp q Pp q Npq+ Mp q+* LXpq Kp q Ipq Hpq Gbpq D Bpq Apq @[pq ?pq =p q <p q ;ep q 9TR 8p q 6p q 5pq 3  1p q 0p q /hp q .*p q ,p q +p q )4 '#pq $pq "@pqpq #jpq "@pq 2pq "-pq "@p q p q "@pq p q "@pq tp q"@pq &pq p q+ p q+ mp q+ 0p q+ p q+ p q+ wp q+ :p q+ pq+ p q+ p q+ p q+5P C](MODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%4mc[test0MemByteLocC, 0];mc[test1MemByteLocC, 60];mc[test2MemByteLocC, 120];mc[test3MemByteLocC, 200];mc[ifuLHmaskC, 3777];* IFU mem left half on low 11 bits of Bmux* Bit definitions for each exception: The exception handling code assumes "not ready" is always ok.mc[exceptions.kfault3, b0];mc[exceptions.FGPe3, b1];mc[exceptions.resched3, b2];mc[exceptions.RamPe3, b3];mc[exceptions.kfault2, b4];mc[exceptions.FGPe2, b5];mc[exceptions.resched2, b6];mc[exceptions.RamPe2, b7];mc[exceptions.kfault1, b8];mc[exceptions.FGPe1, b9];mc[exceptions.resched1, b10];mc[exceptions.RamPe1, b11];mc[exceptions.kfault0, b12];mc[exceptions.FGPe0, b13];mc[exceptions.resched0, b14];mc[exceptions.RamPe0, b15];gp->zN aqpq _pq ^pq ]Kpq Zp q+* Wd VDpq+pq Upq+pq Rpq+pq QNpq+pq Npq+pq Mpq+pq Kpq+pq Ipq+pq FC/" MODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%5* June 17, 1979 4:25 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++IFU TEST REGISTER Definitions%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++mc[test.parity, b8];mc[test.fault, b9];mc[test.memAck, b10];mc[test.makeFD, b11];mc[test.myfh, b12];mc[test.mysh, b13];mc[test.en, b14];mc[test.myfh', 0];* zero turns on fh, 1 bit turns it offmc[test.mysh', 0];* zero turns on sh, 1 bit turns it offmc[test.FH, OR[test.en!,test.myfh'!, test.mysh!] ];* enable, fh' (disable sh)mc[test.SH, OR[test.en!, test.mysh'!, test.myfh!] ];* enable, sh' (disable fh)mc[test.FHSH, OR[test.en!, test.mysh'!, test.myfh'!] ];* enable, fh', sh'mc[test.FhAck, OR[test.Fh!, test.memAck!] ];* enable, fh, memAckmc[test.FhAckFd, OR[test.FhAck!, test.MakeFd!] ];* enable, fh, memAck, MakeFdmc[test.FhFd, OR[test.Fh!, test.MakeFd!] ];* enable, fh, MakeFdmc[test.ShAck, OR[test.Sh!, test.memAck!] ];* enable, sh, memAckmc[test.ShAckFd, OR[test.ShAck!, test.MakeFD!] ];* enable, sh, memAck, MakeFdmc[test.ShFd, OR[test.Sh!, test.MakeFd!] ];* enable, sh, MakeFdgp->zN bAq a? _ ^? ]Kp q \p q Zp q Yp q XUpq Wpq Upq Tp q& S_p q& R"pq(3 Ppq)3 Op q*3 M,p q3 Kp q"3 Jpq3 H6p q3 Fp q"3 Epq3T C:$MODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%6* June 18, 1979 9:40 AM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++IFU Opcode and Entry Point constantsThe opATxx constants are the absolute IM address for the opcode whose IFADM field in the IFU ram hasthe value xx. Eg., if an opcode has an Ifadm value = 14, then opAt14 is the absolute location of thatopcode's entry point in IM.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++* These are entry point declarationsmc[opAt1, 177777];* IFADM=1mc[opAt13, 54];* IFADM=13mc[opAt14, 60];* IFADM=14mc[opAt15, 64];* IFADM = 15mc[opAt17, 74];* IFADM = 17mc[opAt63, 314];* IFADM = 63mc[opAt70, 340];* IFADM = 70mc[opAt22, 110];* IFADM = 22* entry point values for instruction set 3mc[is3KfaultLocC, 0];mc[is3FGParityLocC, 4];mc[is3reschedLocC, 14];mc[is3notReadyLocC, 34];mc[is3ramPElocC, 74];* Base entry point values (ie., the "instruction set bits" have been removed)mc[KfaultBaseLocC, 0];mc[FGParityBaseLocC, 4];mc[ReschedBaseLocC, 14];mc[notReadBaseLocC, 34];mc[ramPeBaseLocC, 74];mc[dispatchLocBaseMask, 77];* base loc = (dispatchAddr) and (dispatchLocBaseMask)* These are opcode declarationsmc[opPause, 0];mc[jump0, 21];* jump .mc[jumpM1, 22];* jump .-1mc[jump1, 23];* jump .+1mc[opNoop, 24];* no jumpmc[opNoopL2, 25];* no jump length 2mc[opNoopL3, 26];* no jump, length 3mc[jumpL2, 27];* jump .+1, length 2mc[jumpML2, 30];* jump .-1, length 2mc[fast1, 31];* one byte, fastmc[fastJfail, 32];* 2 byte failing jump (resets pcF)mc[fastJ, 33];* succeed jump (1 or 2 bytes)mc[fastMJ, 34];* succeed jump to .-mc[fastHalt,35];* pause instr that invokes "error"mc[fastExit, 36];* branch to afterDispatch IF CNT=0&-1mc[fastFetch, 37];* force stack <0, FETCH _ STACKmc[fastStore, 40];* check that MD=stack, mem[stack]_stack, stack_stack+1mc[opSign3, 41];* 3 byte, sign, no encoded constantgp->zN bAq a?!_p$ ]KqpqZ \f Z Y? W$ Tpq  S_pq R"pq Ppq Opq Nipq M,pq Kpq Is1( H6p q Fpq Epq D}pq C@p q @M ?pq >Jpq = pq ;pq :p q 9Tpq5 6 4^pq 3 pq  1pq 0pq /hpq  .*pq  ,pq  +pq  *rpq  )4pq  'pq " &pq  %|pq  $>pq " #pq % !pq  pq 6 Hpq #B E3MJMODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%7* June 24, 1979 5:41 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++IFU field declarationsDefines fields mostly for IfuMemory.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++mc[mos.ifuCmmd, b0];* the bit that causes MOS_ to address Ifu rather than junk IO.set[ifu.InstrSetSize, 2];set[ifu.SetInstrSetShift, 10];set[ifu.GetInstrSetShift, 13];mc[ifu.InstrSetMask, 3];set[ifu.paShift, 12];set[ifu.paSize, 1];set[ifu.AdShift,0];set[ifu.AdHi2Shift, 10];set[ifu.AdLow8Shift, 0];mc[ifu.AdMask,1777];set[ifu.signShift, 17];set[ifu.signSize, 1];set[ifu.pe0Shift, 16];set[ifu.pe1Shift, 15];set[ifu.pe2Shift, 14];mc[ifu.peMask, b1,b2,b3];set[ifu.ILShift, 12];set[ifu.ILSize, 2];mc[ifu.ILMask, 3];set[ifu.rbSelSize, 1];set[ifu.rbSelShift, 11];set[ifu.memBK34Size, 1];set[ifu.memBK34Shift, 10];set[ifu.memBShift, 6];set[ifu.memBLow2Shift, 6];set[ifu.memBHi2Shift, 10];mc[ifu.memBMask, 17];mc[ifu.rbSelMask, b12];set[ifu.typeShift, 4];set[ifu.typeSize, 2];mc[ifu.typeMask, 3];set[ifu.pauseShift, 5];set[ifu.pauseSize, 1];mc[ifu.pauseMask, 1];set[ifu.jumpShift, 4];mc[ifu.jumpMask, 1];set[ifu.jumpSize, 1];set[ifu.nShift, 0];mc[ifu.nMask, 17];set[ifu.nSize, 4];* June 17, 1979 4:25 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++IFU Memory Construction MacrosThese macros aid in the construction of Ifu memory values. Ie., they appear in the microcode wherethe Ifu memory is being initialized with opcodes. They work by constructing assembly-time values foreach field in the Ifu memory. Then they construct a constant (done in composeIfuWd) that gets loadedinto RM at run time. The macro endIfuWd understands the calling conventions for the subroutineputIfuWd.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++m[newIfuWd, set[mypa,0]set[myad,0]set[mysign,0]set[mylength,0]set[mymemb,0]set[mypause,0]set[myjump,0]set[myn,0]];m[ifPa, set[mypa, lshift[#1,ifu.paShift]]];gp->zN bAq a?&_p ]Kq$ \? Y)p qj> Vpq Uppq T3pq Rpq Pp q Op q Mp q LXp q Kpq Ip q Gp q Fp q D}p q C@p q Bp q @p q >p q =vp q <8p q 9p q 8p q 7Bpq 6pq 3p q 2pq 1ypq 0;p q .p q ,p q +p q *rp q (`p q '#p q %p q #p q "p q !Yp q p q  pq p q  ?$mp qc e wGp q :pq7 p q? pq [ pq% yD]HMODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%8m[ifAd, set[myad, and[not[#1],ifu.adMask!]]];m[ifAdHi, set[myad, or[myad, and[and[177400,not[#1]],ifu.adMask!]]]];m[ifAdLow, set[myad, or[myad, and[and[377,not[#1]],ifu.adMask!]]]];m[ifSign, set[mysign, lshift[#1,ifu.signShift]]];m[ifLength, set[mylength, lshift[and[not[#1],ifu.ILMask!],ifu.ILShift]]];m[ifMemB, set[mymemb, lshift[and[xor[ifu.rbSelMask!, #1],ifu.memBMask!],ifu.memBShift]]];m[ifPause, set[myPause, lshift[and[not[#1],ifu.pauseMask!],ifu.pauseShift]]];m[ifJump, set[myJump, lshift[and[not[#1],ifu.jumpMask!],ifu.jumpShift]]];m[ifN, set[myN, and[#1, ifu.nMask!]]];m[composeIfuWd,ilc[(rscr _ and[or[mypa,myad],177400]C)]ilc[(rscr _ (rscr) or(and[or[mypa,myad],377]C))]ilc[(rscr2 _ and[177400, or[mysign,mylength,mymemb,mypause,myjump,myn]]C)]ilc[(rscr2 _ (rscr2) or (and[377, or[mysign,mylength,mymemb,mypause,myjump,myn]]C))]]m[endIfuWd,composeIfuWd[]ilc[(t_and[#2,377]c)]ilc[(t_tor (and[lshift[#1,10],1400]C))]ilc[(call[putIfuWd])]];gp->zN bAqpq' apq= _pq: ^pq) ]Kpq? \pqQ ZpqD Ypq@ XUpq! Wp qU(T0S_JR"TP OpNiq M,K'JIs G; b~MODEL 1: ifuDefs.mcJune 17, 1981 3:30 PM%9* January 2, 1979 1:46 PM* These macros support the use of the test registerm[iTick,ilc[(FGbits _ (#1))]ife[#0,2,(ilc[(FGBits_(FGbits)OR(lshift[#2, 10]C))]),]ilc[(call[itTick])]];m[iNewPc,ilc[(FGbits _ (#1))]ife[#0,2, ilc[(FGBits _ (FGbits) OR (lshift[#2, 10]C) )],]ilc[(call[itNewPc])]];m[iReset,ilc[(FGbits _ (#1))]ife[#0,2, ilc[(FGBits _ (FGbits) OR (lshift[#2, 10]C) )],]ilc[(call[itReset])]];m[iJump,ilc[(FGbits _ (#1))]ife[#0,2, ilc[(FGBits _ (FGbits) OR (lshift[#2, 10]C) )],]ilc[(call[itJump])]];m[iJumpData,ilc[(FGbits _ (#1))]ife[#0,2, ilc[(FGBits _ (FGbits) OR (lshift[#2, 10]C) )],]ilc[(call[itJumpData])]];m[iData,ilc[(FGbits _ (#1))]ife[#0,2, ilc[(FGBits _ (FGbits) OR (lshift[#2, 10]C) )],]ilc[(call[itData])]];* Initialize Ifu memory: initIfuM[location, leftHalf, rightHalf]m[initIfuM,ilc[(t _ #1c)]ilc[(rscr_and[#2,177400]c)]ilc[(rscr_(rscr)OR(and[#2,377]c))]ilc[(call[putIfuLH])]ilc[(t _ #1c)]ilc[(rscr_and[#3,177400]c)]ilc[(rscr_(rscr)OR(and[#3,377]c))]ilc[(call[putIfuRH])]];gp->zN bAq a4 ^pq]K\6ZY XUpqWU:TS_ R"pqPO:NiM, KpqJIs:H6F EpqD}C@:B@ ?pq>J= :;: 8@ 5pq4^ 3 1"0/h .*,"+*r ).>IfuRamSubrs.mcJune 17, 1981 3:34 PM%1* INSERT[D1ALU.MC];* TITLE[Ifu1];* INSERT[PREAMBLE.MC];%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++CONTENTSRoutineDESCRIPTIONputIfuLHIfuMLH[t] _ rscrputIfuRHIfuMRH[t] _ rscrgetIfuLHt IfuMLH[t]getIfuRHt _ IfuMRH[t]initIfuM1Thru3Initialize Ifum locs 1-3 in current instruction set.initIfuM1Thru16Initialize IfuM locs 1-16B in current instruction setifuBackgroundWrite halt opcodes into Ifu memorygetIfuHaltReturns t, rscr = ifuHalt opcode (for IfuMemory)initIfuMemoryWrites selected opcodes into Ifu memoryputIfuWdWrites (rscr,,rscr2) into IfuMemory at TifuAddParitySet parity bits for IfumLH, IfumRH (rscr, rscr2)ifuCountOnesCount the number of one bits in t%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++June 17, 1981 3:34 PMAdd opSign3 instruction.February 1, 1980 8:06 PMFix miscellaneous comments in fast opcodes init.October 11, 1979 5:08 PMSet Ifum[opPause] for inst ruction set 3 -- needed by event counters code.June 15, 1979 4:35 PMChange putIfuLH, putIfuRH, getIfuLH, getIfuRH to use mos.ifuCmmdJune 5, 1979 1:04 PMChange symols ifu.Length* to ifu.IL*.June 5, 1979 11:41 AMAdd calls to disableConditionalTask before writing Ifumemory, initializing regular memory system.May 4, 1979 10:12 AMAdd calls to resetIfu after writing IfuM.May 3, 1979 11:35 AMAdd missing composeIfuWd[], which should have been part of earlier fix to invoke putIfuWddirectly.May 3, 1979 9:59 AMRemove extraneous endIfuWd[] from initIfum0Thru16.May 3, 1979 9:07 AMMake initIfuM1Thru* use iUsingInstrSet and call putIfuWd directly.April 25, 1979 1:00 PMAdd fastExit, fastFetch, fastStore opcodes.April 23, 1979 9:33 AMChange InitIfum1thru3 to use the standard macros.April 22, 1979 5:11 PMCreate this file from code in ifu1-ifu3.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ gp +JJ = 1;@ :19T% 816a 514^) 3 11Y 0 /h@.*2 ,@+B *r@)4+ '@&1 %|1$>( #? CH|IfuRamSubrs.mcJune 17, 1981 3:34 PM%2* January 15, 1979 4:54 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Ifu Memory subroutinesThis code doesn't reset the Ifu. Caller Beware!Enter with T = 10 bit IFU address. If writing ifum, rscr = 16 bit valueExit W/ T = 16 bit value if reading IFUM.Clobbers T%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++putIfuLH: subroutine;* t = addr, rscr = valuet _ t OR (mos.ifuCmmd);* ifu data, not junk ioMOS _ t;* this sets the instruction set from B[6:7]t _ lsh[t, 10];* left justify the bytebrkins _ t;* set brkinsnoop;* wait for the address to filter to ramIFUMLH _ rscr;* must keep data constant on B muxreturn, B _ rscr;* for two cycles.putIfuRH: subroutine;* t = addr, rscr = valuet _ t OR (mos.ifuCmmd);* ifu data, not junk ioMOS _ t;* this sets the instruction set from B[6:7]t _ lsh[t, 10];* left justify the bytebrkins _ t;* set brkinsnoop;* wait for the address to filter to ramIFUMRH _ rscr;* must keep data constant on B muxreturn, B _ rscr;* for two cycles.getIfuLH: subroutine;* t = addr, returns lh valuet _ t OR (mos.ifuCmmd);* ifu data, not junk ioMOS _ t;* this sets the instruction set from B[6:7]t _ lsh[t, 10];* left justify the bytebrkins _ t;* set brkinsnoop;* wait for the address to filter to ramreturn, t _ not(IFUMLH');getIfuRH: subroutine;* t = addr, returns rh valuet _ t OR (mos.ifuCmmd);* ifu data, not junk ioMOS _ t;* this sets the instruction set from B[6:7]t _ lsh[t, 10];* left justify the bytebrkins _ t;* set brkinsnoop;* wait for the address to filter to ramreturn, t _ not(IFUMRH'); gp +=v<8! 8(7 6oU5132!1y+ ..- ,U+E*(! &O.% #U"!Y ! .c &Um! 4 Uf) ! + 3/ <]IfuRamSubrs.mcJune 17, 1981 3:34 PM%5newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[2]; ifMemB[3]; ifPause[0]; ifJump[1]; ifN[17];composeIfuWd[];t _ 10C;call[putIfuWd], t _ t or (stack);* opcode at iUsingInstrSet,,11: length=1, jumpnewIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[3]; ifPause[0]; ifJump[1]; ifN[17];composeIfuWd[];t _ 11C;call[putIfuWd], t _ t or (stack);* opcode at iUsingInstrSet,,12: length=1, jump, n=2newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[3]; ifPause[0]; ifJump[1]; ifN[2];composeIfuWd[];t _ 12C;call[putIfuWd], t _ t or (stack);* opcode at iUsingInstrSet,,13: length=1, jump, n=2newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[3]; ifPause[0]; ifJump[1]; ifN[3];composeIfuWd[];t _ 13C;call[putIfuWd], t _ t or (stack);noop;* for placement.* opcode at iUsingInstrSet,,14: length=1, sign, jump, n=17newIfuWd[];ifPa[0]; ifAd[15]; ifSign[1]; ifLength[1]; ifMemB[3]; ifPause[0]; ifJump[1]; ifN[17];composeIfuWd[];t _ 14C;call[putIfuWd], t _ t or (stack);* opcode at iUsingInstrSet,,15: length=1newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[3]; ifPause[0]; ifJump[0]; ifN[17];composeIfuWd[];t _ 15C;call[putIfuWd], t _ t or (stack);* opcode at iUsingInstrSet,,16: length=1newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[3]; ifPause[0]; ifJump[0]; ifN[17];composeIfuWd[];t _ 16C;call[putIfuWd], t _ t or (stack);call[resetIfu];* clear breakPending, which gets set as a result ofwriting IfuM.pReturnP[]; gp +;=v <8U:98! 6)4 3U2L1/! -V), *U)(`'#!%+3 $ #j  " BFIfuRamSubrs.mcJune 17, 1981 3:34 PM%6* June 5, 1979 11:43 AM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuBackgroundThis subroutine causes all the locations in the Ifu memory to contain parity-valid instructions thatwill cause the processor to get an error (invoke the ERROR code) if any of them gets executed. Thisdetects the case where the ifu starts executing an uninitialized opcode.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuBackground:pushReturn[];call[disableConditionalTask];call[resetIfu];t _ 1777C;cnt _ t;ifuBackgroundL:noop;call[getIfuHalt];* Returns rscr2 = ifumLH, rscr = ifumRH.t_cnt;call[putIfuWd], stack+1_t;* t = address to write. Save cnt sincecnt _ stack&-1;* putIfuWd will clobber it.loopUntil[CNT=0&-1, ifuBackgroundL];call[resetIfu];* clear breakPending, which gets set as a result ofwriting IfuM.returnP[];* April 19, 1979 11:10 AM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getIfuHaltThis subroutine returns rscr2 = ifumLH, rscr = ifumRH for an opcode that causes the processor to startexecuting code that invokes an error. Parity has not been computed.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getIfuHalt:pushReturn[];newIfuWd[];ifPa[0]; ifAd[22]; ifSign[0]; ifLength[1]; ifMemB[0]; ifPause[1]; ifJump[0]; ifN[17];composeIfuWd[];t _ rscr2;returnP[]; gp +Jqf = D ;? :p 9Tq 8 6U54^ 3 T 0E37IfuRamSubrs.mcJune 17, 1981 3:34 PM%7* June 17, 1981 3:34 PM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++initIfuMemoryInitialize the Ifu memory to contain opcodes for the various tests used in the ifu diagnostic. Themajority body of code in this subroutine consists of macros that construct integer valuescorresponding to the proper bits for the Ifu memory. The endIfuWd macro invokes the subroutineputIfuWd to write those values into the Ifu.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++initIfuMemory: subroutine;pushReturn[];call[disableConditionalTask];call[resetIfu];* pause (length 1)iicPause:newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[0]; ifPause[1]; ifJump[0]; ifN[17];endIfuWd[3, opPause!];* jump . (length 0)iicJump0:newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[0]; ifPause[0]; ifJump[1]; ifN[0];endIfuWd[3, jump0!];* write the constructed value into location jump0 ofIfu memory* jump.-1 (length=1)iicJumpm1:newIfuWd[];ifPa[1]; ifAd[15]; ifSign[1]; ifLength[1]; ifMemB[0]; ifPause[0]; ifJump[1]; ifN[17];endIfuWd[3, jumpM1!];* jump.+1 (length=1)iicJp1:newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[0]; ifPause[0]; ifJump[1]; ifN[1];endIfuWd[3, jump1!];* opNoop (length=1)iicOpL1:newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[1]; ifMemB[0]; ifPause[0]; ifJump[0]; ifN[4];endIfuWd[3, opNoop!];* opNoopL2 (length=2)iicopL2:newIfuWd[];ifPa[1]; ifAd[15]; ifSign[0]; ifLength[2]; ifMemB[0]; ifPause[0]; ifJump[0]; ifN[15];endIfuWd[3, opNoopL2!];noop;* for placement* opNoopL3 (length=3)iicopL3:newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[3]; ifMemB[0]; ifPause[0]; ifJump[0]; ifN[6];endIfuWd[3, opNoopL3!];* jumpL2 (length=2)iicJpL2:newIfuWd[];ifPa[0]; ifAd[15]; ifSign[0]; ifLength[2]; ifMemB[0]; ifPause[0]; ifJump[1]; ifN[1];endIfuWd[3, jumpL2!];* jumpML2 (length=2)iicJmL2:newIfuWd[];ifPa[0]; ifAd[15]; ifSign[1]; ifLength[2]; ifMemB[0]; ifPause[0]; ifJump[1]; ifN[17];endIfuWd[3, jumpML2!];* opSign3 (length=3)iicOpSign3: gp +Jq = U; 9Tpq 8p6q 5T4^ 1pq 0p/hq .*T, *rpq )4p'q &U%|$>+ !pq pHq  T Rpq pq T\ pq pfq )U  ppq 3p q C]IfuRamSubrs.mcJune 17, 1981 3:34 PM%8newIfuWd[];ifPa[0]; ifAd[15]; ifSign[1]; ifLength[3]; ifMemB[0]; ifPause[0]; ifJump[0]; ifN[17];endIfuWd[3, opSign3!];noop;* for placement gp +J = U;:+ 8pq 6p q5 4^U3 1+ /hpq .*p q, +U*r)4+ &pq %|p q$> #U! +  pq p q RU+\+3    DVIfuRamSubrs.mcJune 17, 1981 3:34 PM%10* April 20, 1979 4:05 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++putIfuWdWrite both left and right half of IFUM.Enter with RSCR=ifuLH, RSCR2=ifuRH, T= ifu Address. Caller is responsible for resetting the Ifubefore calling this routine! Call ifuAddParity to correctly set the parity bits for this word ofIFUM. Use putIfuLh and putIfuRh to write into IFUM.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++putIfuWd: subroutine;pushReturnAndT[];call[ifuAddParity];* compute correct parity bits.* now write rscr into IFUMLH and rscr2 into IFUMRH. Address is in StackputIfuWdFinishUp:call[putIfuLh], t _ stack;* t _ ifu address, rscr = value for LHrscr _ rscr2;call[putIfuRH], t _ stack;* t = addr, rscr = value for RHpReturnP[]; gp +J = p ;q":8 +-654^3  0B /hp .*q&+,*r)+ )4' &$>*- #!   $+! R(+\ +f) +  > MC\IfuRamSubrs.mcJune 17, 1981 3:34 PM%12* January 7, 1979 6:33 PMifuCountOnes: subroutine;* count the number of one bits in t.* CLOBBER t, cnt. Return value in T. Push entering value of t onto stack.pushReturn[];cnt_17s;stack+1_t;t _ t-t;icoL:skpif[R EVEN], stack;t _ t+1;* increment count of one bits when lsb of stack is oneloopUntil[CNT=0&-1, icoL], stack _ (stack) rsh 1;pReturnP[]; gp +J ;p q +p :q 9T86 54^3 1 0p q +p qp/hq .*,+ *rp q +p )4q '&%| $>#! 7p q +p q+~A +%  K  p q +p qU  p q +p y8],IfuStepSubrs.mcJune 18, 1981 10:00 AM%4* enter w/ t = value for new pcpushReturnAndT[];* keep new pc value in rscrcall[iAddFGParity], t _ test.Sh;IFUTest _ t;* iAddFGParity returned FG value in TifuTick;PcF _ stack;PcF _ stack;pReturnP[];itNextDataSH: subroutine;* _NexData, SHpushReturn[];call[iAddFGParity], t _ test.Sh;IFUTest _ t;ifuTick;t _ ID;noop;returnP[];itNoopFH: subroutine;* tick, FH, BmuxRM _ stack (originally from t)pushReturnAndT[];call[iAddFGParity], t _ test.Fh;IFUTest _ t;ifuTick;B_stack;B_stack;pReturnP[];itNoopFhSh: subroutine;* tick, FH, SH, BmuxRM _ tpushReturnAndT[];call[itNoopFH], t_stack;call[itNoopSH], t_stack;pReturnP[];itNoopSH: subroutine;* tick, SH, Bmux _ tpushReturnAndT[];call[iAddFGParity], t _ test.Sh;IFUTest _ t;ifuTick;B_stack;B_stack;pReturnP[];itResetFH: subroutine;* IfuReset, FHpushReturn[];call[iAddFGParity], t _ test.Fh;IFUTest _ t;ifuTick;ifuReset;ifuReset;returnP[];itResetSH: subroutine;* IfuReset, SHpushReturn[];call[iAddFGParity], t _ test.Sh;IFUTest _ t;ifuTick;ifuReset;ifuReset;returnP[];itSetFGFDSH: subroutine;* FG[0:7]_t, MakeF_D, SHpushReturnAndT[];rscr _ lsh[t, 10];* left justify the byte in rscrsetCtemp[test.Sh, test.makeFD];call[iAddFGParity], t _ (rscr) OR (cTemp);IFUTest _ t;ifuTick;noop;noop;pReturnP[];itSetFGFH: subroutine;* FG[0:7]_t, FHpushReturnAndT[];rscr _ lsh[t, 10];* left justify the byte in rscr^gp+="N bAqa+_^ +%]K\ Z Y Wp q +p Uq TS_ R"PONi Kpq +p,JqIsH6 FED}C@ Bp q +p@q?>J= ;pq +p:q9T8 654^3 /p q +p .q -V, *)(`'# %p q +p $q #j"-  t7 p q +p~qA+ * K  p q +p  q +d y>]1IfuStepSubrs.mcJune 18, 1981 10:00 AM%5call[iAddFGParity], t _ (rscr) or (test.Fh);IFUTest _ t;ifuTick;noop;noop;pReturnP[];itSetFGSH: subroutine;* FG[0:7]_t, SHpushReturnAndT[];rscr _ lsh[t, 10];* left justify the byte in rscrcall[iAddFGParity], t _ (rscr) or (test.Sh);IFUTest _ t;ifuTick;noop;noop;pReturnP[];itStep: subroutine;* TEST _ t* enter w/ T= value for Test registerpushReturnAndT[];call[iAddFGParity];IFUTest _ t;ifuTick;noop;noop;pReturnP[];^gp+="NbAq,a _^]K\ Zp q +p YqXU+W,U TS_R"P M,pq +p Kq%JIsH6 FED}C@  A 4'zIfuStepSubrs.mcJune 18, 1981 10:00 AM%6* June 18, 1981 10:00 AM%Simulation subroutines, originally from ifu2.mc%itTick: subroutine;saveReturn[klink];call[incClock];call[iAddFGParity], t _ FGbits;ifuTest _ t;ifutick;b _ BmuxRM;B _ BmuxRM;returnUsing[kLink];itData: subroutine;* itData, itJumpData, and itJump shouldsaveReturn[klink];* never be called when test.Fhcall[incClock];call[iAddFGParity], t _ FGbits;t and (test.myFh);* we shouldn't be called during test.Fhskpif[ALU#0];* test.myFh (a "one bit") disables Fherror;ifuTest _ t;ifutick;b _ BmuxRM, t _ ID;noop;returnUsing[kLink];itJumpData: subroutine;saveReturn[kLink];call[incClock];call[iAddFGParity], t _ FGBits;t and (test.myFh);* we shouldn't be called during test.Fhskpif[ALU#0];* test.myFh (a "one bit") disables Fherror;ifuTest _ t;ifutick;IfuJump[0], B _ BmuxRM, T _ ID;noop;iAnyIJumpRet:returnUsing[kLink];itJump: subroutine;saveReturn[kLink];call[incClock];call[iAddFGParity], t _ FGbits;t and (test.myFh);* we shouldn't be called during test.Fhskpif[ALU#0];* test.myFh (a "one bit") disables Fherror;ifuTest _ t;ifutick;IfuJump[0], B _ BmuxRM;noop;returnUsing[kLink];itNewPc: subroutine;saveReturn[kLink];call[incClock];call[iAddFGParity], t _ FGbits;ifuTest _ t;ifutick;PcF _ BmuxRM;PcF _ BmuxRM;returnUsing[kLink];itReset: subroutine;saveReturn[kLink];call[incClock];call[iAddFGParity], t _ FGbits;^gp+="N bAq a _/ ^ Ypq XWVDU SR QN P Mpq +'LX+KIH+'Gb +%F$D CBlA.? =vp q <8:98+'7B +%64 32L1 /p .q ,pq *)(`'#+'% +%$#j "- t pq ~A  K   pq   D \ :](IfuStepSubrs.mcJune 18, 1981 10:00 AM%7ifuTest _ t;ifutick;IfuReset, B _ BmuxRM;IfuReset, B _ BmuxRM;returnUsing[kLink];^gp+="NbAq a_^]Kz [o *IfuSubrs.mcJune 18, 1981 9:59 AM%1 TITLE[IfuSubrs];%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++CONTENTSTESTDESCRIPTIONget1Rand:Get one random numberiGetISubrScr:Return current value of iSubrScrincClockIncrement a counter (clockCount) and pulse TIOA for scoping if count has rightvalueiPat16:initialize pat16XnextPat16:return t = new pattern, ALU=0 if no more patternsgetPat16:return current patterniPat8:Initialize pat8XnextPat8:Return new 8 bit patterngetPat8:Return current 8 bit patterniIaddr:Initialize iAddrXnextIAddr:Return next IfuM addressgetIAddr:Return current ifuM addressKfaultXMemory fault ifu entry point for instruction set X (X IN [0..3])FGParityXFGparity ifu entry point for instruction set X (X IN [0..3])ReschedXResched ifu entry point for instruction set X (X IN [0..3])NotReadyXNot ready ifu entry point for instruction set X (X IN [0..3])RamPEXRam PE ifu entry point for instruction set X (X IN [0..3])op0:Ifu opcode destinationop377:Ifu opcode destinationopIfAd10:Ifu opcode destination w/ ifuAd = 10 (address bits in IfuM). fast-Exit.opIfAd11:Ifu opcode destination w/ IfuAd = 11. fast-FetchopIfAd12:Ifu opcode destination w/ IfuAd = 12. fast-StoreopIfAd13:Ifu opcode destination w/ IfuAd = 13. jump-FailopIfAd14:Ifu opcode destination w/ IfuAd = 14. unconditional-JumpopIfAd15:Ifu opcode destination w/ IfuAd = 15. most opcodes dispatch to hereopIfAd16:ifu opcode destination w/ IfuAd = 16. jump-SucceedopIfAd20Err:ifu opcode destination w/ IfuAd = 20. pause-Halt (should never get here)afterDispatch:returns control after ifuJump via return link kept in KLINKreadMufBit:Reads muffler bit, enter w/ t = addressreadMuffler:Returns a muffler byte; enter w/ t = muffler address.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%June 18, 1981 9:59 AMMove incClock from ifuStepSubrs to here.June 18, 1981 9:23 AMConstruct this file out of ifu1.mcMay 18, 1981 2:25 PMFix nextPat to invoke cycleRandV to get better performance from the random number generator.February 1, 1980 7:58 PMFix stack handling bug in return code of addressing test. Fix old bug in fastStore code that wasfetching rather than storing.February 1, 1980 7:48 PMAdd code to mask out unwanted bits from getIfuLH in addressing test.February 1, 1980 6:37 PMAdd iMemAddrs, an addressing logic test.February 1, 1980 5:06 PMImprove the set of patterns generated by pat16.September 19, 1979 1:13 PMReset expectedDispatch<0 after invoking iSingleStepTest.September 19, 1979 12:55 PMMove beginIfu1 to the beginning of the file, add more and better comments, and set upiSingleStepTest to loop 400 times.September 17, 1979 5:29 PMAdd iSingleStepTest.July 3, 1979 1:53 AMIncrement return link in checkException by 1 -- because afterdispatch will also decrement it & weneed compatability. This increment occurs after the potential error check where the link has beendecremented to make error interpretation easier.July 3, 1979 1:17 AMDecrement return link in checkException by 1 -- so that it points to where we came from ratherthan where to return to, which is irrelevant..July 3, 1979 12:06 AMAdd code to enable dynamically selected exception conditions.June 29, 1979 11:46 AM gp *;tN bAq aB_ ]K Zp q Yp  q XUp qN W Up q Tp  q1 S_p q R"p q Pp q Op q Nip q M,p  q Kp q Jp q@ Isp q< H6p q; Fp q= Ep q: D}p q C@p q Bp qG @p q0 ?p q0 >Jp q/ = p q8 ;p qC :p q2 9Tp  qH 8p  q; 6p  q' 5p  q5 4^B 1 01/h( .*1," +1*r\ )41'a & %|1$>D #1!( 1H/  18 1RU " 1 \1a b 0 f1)^ . 1 p= 3 DR]xIfuSubrs.mcJune 18, 1981 9:59 AM%2Modify afterDispatch to save POINTERS into (stack+1), but to return control with stkp = enteringvalue. Do this since afterDispatch resets RBASE to defaultRegion, and some tests want to check thevalue that RBASE got set to when the IfuJump occured.June 20, 1979 9:14 AMAdd call to resetIfu in iMemRandAddrs and cause beginIfu1 to invoke iMemRandAddrs.June 20, 1979 8:50 AMAdd ifuLHmaskC masking to data in iMemRandAddrsJune 20, 1979 7:35 AMAdd random address generation test (iMemRandAddrs)June 19, 1979 10:34 AMFix register clobbering bug in new version of ifuMemRW.June 18, 1979 8:56 AMFix bug in 3rd pattern of nextPat16.June 17, 1979 4:04 PMAdd entry points for all the exception conditionsJune 15, 1979 3:24 PMEnable random patterns in iMemRWJune 5, 1979 12:43 PMRemove i.testCase2L since test2 has been removed from default diagnostic.June 5, 1979 11:31 AMAdd disableConditionTaskMay 30, 1979 10:08 AMAdd random numbers to pat16 code; diddle iMemRW to reset the Ifu only once.May 9, 1979 9:05 AMFix subroutine mode error in ifuMScopeLoop. Move contents section to top of file & add morecomments.May 4, 1979 10:57 AMAdd scope loop for checking Ram speed.May 3, 1979 8:44 AMAdd calls to setIUsingInstrSet before invoking initIfuM1Thru(3,16)April 26, 1979 9:53 AMAdd pat8 subroutines.April 25, 1979 12:13 PMAdd fastExit, fastFetch, fastStore code.April 24, 1979 5:27 PMRemove references to dispatchOffset, simplify afterDispatch.April 22, 1979 5:10 PMMove iAddFGParity thru itStep into ifuStepSubrs.mcFebruary 7, 1979 10:35 AMAdd breakpoints to rampe, kfault, resched entries; explicitly place all the entry points for theinstructions.February 6, 1979 2:16 PMAdd requisite noop after PcF_.February 5, 1979 12:54 PMAdd ifAd20 -- ifu pause/halt codeFebruary 5, 1979 9:59 AMChange opifad13,14,16 to do ifuJumps directly.January 18, 1979 6:44 PMFix misc. bugs in pattern16, muffler bit reading codeJanuary 17, 1979 3:52 PMMore Rev-Bb mods: define exception code for instrSet 1 (locations 200,204,214,234,274). DefineitMosFhSh.January 15, 1979 4:52 PMRev-Bb mods: instrSet bits, complemented, are or'd into Exception addresses. InstrSet bits 2,3pick bytes right to left. Cycled 0 pattern for Ifu memory test.% gp *;tN1bAq` ac _5 ^1]KR \1Z/ Y1XU3 W1U7 T1S_$ R"1P1 O1Ni M,1KI J1Is H61FK E1D}\ C@ B1@& ?1>JB = 1; :19T( 816< 514^2 3 11` 0 /h1.* ,1+! *r1)4. '1&5 %|1$>_ # !1 _ H@   CKaIfuSubrs.mcJune 18, 1981 9:59 AM%3* June 18, 1981 9:59 AMget1Rand: pushReturn[];getRandom[];returnP[];iGetISubrScr: subroutine;RBASE _ rbase[iSubrScr];return, t _ iSubrScr, RBASE _ rbase[defaultRegion];* move elsewhereincClock: subroutine;RBASE _ rbase[clockCount];t _ clockCount _ (clockCount)+1;t - (triggerCount);skpif[ALU#0], TIOA _ triggerZero;TIOA _ triggerValue;return, RBASE _ rbase[defaultRegion]; gp *;tN bAq apq @_ @^ \p q 1Z1Y30p Wq 1U1T1S_1R"!1P1O% K/@QIfuSubrs.mcJune 18, 1981 9:59 AM%4* May 18, 1981 2:25 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iPat16nextPat16getPat1616 bit pattern subroutinesiPat16initialize pat16XnextPat16return t = new pattern, ALU=0 if no more patternsgetPat16return current patternEventually these will move to postamble.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iPat16: subroutine;* initialize 16 bit patternt _ cm1;return, pat16X _ t;nextPat16: subroutine;* rtns next 16 bit patternsaveReturn[Klink];top level;RBASE _ rbase[pat16X];t _ pat16X _ (pat16X) + 1;t - (pat16End1C);* see if done w/ current patternbranch[after1Pat16, ALU>=0], PD _ pat16X;* if not done, see if current pattern is zero* IN [0..pat16End1C)skpif[ALU#0];* init the pattern if this is first time thruskip, t _pat16 _ 1c;* pattern init; set to onet _ pat16 _ (pat16) lsh 1;* left shift a one bitbranch[xitNextPat16ok];after1Pat16:t - (pat16End2C);* see if done w/ pattern 2branch[after2Pat16, ALU>=0];* IN [pat16End2C..pat16End2C)* Pattern 2 = cycled zero bitt # (pat16End1C);* see if first time in Pattern2skpif[ALU#0];pat16 _ 77777C;* set it to only one zero bit for first timepat16 _ t _ lcy[pat16, pat16, 1];* left cycle it onebranch[xitNextPat16ok];after2Pat16:* see if pattern 3t - (pat16End3C);skpif[ALU<=0];branch[after3Pat16];* see if done w/ pattern 4* IN [pat16End2C..pat16End3C): Pattern 3branch[xitNextPat16ok];* real work is done by getPat16after3Pat16:t - (pat16End4C);skpif[ALU<=0];branch[after4Pat16], rscr _ t-t;* all done* IN [pat16End3C..pat16End4C): Pattern 4call[cycleRandV];branch[xitNextPat16ok];* real work is done by getPat16after4Pat16:t - (pat16End5C);skpif[ALU<=0];branch[after5Pat16];* all done* IN [pat16End4C..pat16End5C): Pattern 5branch[xitNextPat16ok];* real work is done by getPat16after5Pat16:t - (pat16End6C);skpif[ALU<=0];branch[xitNextPat16], rscr _ t-t;* all done* IN [pat16End5C..pat16End6C): Pattern 6branch[xitNextPat16ok];* real work is done by getPat16 gp *;tN bAq aB,_p+^+f]K Zq Ypq XUpq1 Wpq U( TB R"pq +PO M,p q +KJ IsH6F+E)+- C@B +-@+?+>J ;p :q+9T 6+r5q+4^ 3 +,1!+0 .*p +q,+ *r+ 'r&q+ $>p #q!  + Hr q+ Rp q + \rq+ p fq)  !+ r pq+ >%]3IfuSubrs.mcJune 18, 1981 9:59 AM%5xitNextPat16ok:rscr _ (pat16X)+1;* put non-zero value in rscrxitNextPat16:returnAndBranch[klink, rscr];* t = current pattern; ALU#0 means value ok gp *;tN bAaq+ _p ^q++ [< ,IfuSubrs.mcJune 18, 1981 9:59 AM%6* February 1, 1980 5:39 PMgetPat16: subroutine;* Enter w/ T = ifu addr. rtn w/ next pattern in T%Currently there are four sets of patterns:pattern1left cycled 1 bitpattern2left cycled 0 bitpattern3left cycled indexpattern4random numberspattern5words of all zeros alternated w/ all onespattern6words of all ones alternated w/ all zerosPattern1 and pattern2 return the same value every time getPat16 is called, given a constant value forpat16X. Ie., the range for pat16X in pattern 1 is [0..pat16End1C), and when pat16X is zero, getPat16always returns 1, when SpatX is one, getPat16 always returns 2, etc.Pattern2 is similar to pattern1 except that it is a bitwise complement, ie., a single zero bit withthe remaining bits all ones.Pattern3 returns the current index left cycled. The calling program provides the index (low 16 bitsonly) in T. The first time pattern3 is in effect, it returns the current index. The next timegetPat16 is called, the cycle count for pattern 3 increments and getPat16 returns the index leftcycled 1, etc.Pattern4 returns a random number.Pattern5 returns a word of all zeros followed by a word of all onesPattern6 returns a word of all ones followed by a word of all zeros%mc[shc.AisT, b2];mc[shc.BisT, b3];set[shc.countShift, 10];mc[shc.maskShiftCount, b4,b5,b6,b7]mc[shc.rmt, shc.BisT!];* deal w/ rm,,tmc[shc.rmrm, 0];RBASE _ rbase[klink];* save return and preserve t.klink _ link;top level;RBASE _ rbase[pat16X];(pat16X)-(pat16End1C);* see which pattern we are usingbranch[get16P2,ALU>=0];* IN [0..pat16End1C)pattern 1* pattern 1 returns a cycled 1 bit.branch[get16PXit], t_pat16;* nextPat16 did our workget16P2:* return pattern 2 or greater(pat16X)-(pat16End2C);branch[get16P3, ALU>=0];* IN [pat16End1C..pat16End2C)pattern 2* pattern 1 returns a cycled 0 bit.branch[get16PXit], t _ pat16;* nextPat16 does our work gp *;tN bAq apq +1 _^*]K+\+Z+Y+ XU+)W+) UpqpqP Se RD Pzpq[ O= M,pq\ K_ J` Is Gbpq EQpq; C@pq; B ?pq >Jpq = p q ;pq :pq + 9Tpq6+5 4^ 10+/h .*+r ,q#++ )4p+q'& %|+r $>q##+\ !DFkIfuSubrs.mcJune 18, 1981 9:59 AM%7* February 1, 1980 5:35 PMget16P3:(pat16X) - (pat16End3C);branch[get16P4, ALU>=0];* IN [pat16End2C..pat16End3C)pattern 3%Pattern3 returns a cycled version of the current index.Begin by moving the current index into curSpattern, and then construct a shifter control valuethat will provide the correct cycle value. Always construct a SHC value that cycles rm,,t.%pat16 _ t;* ENTERED W/ T = low 16 bits of indext _ pat16X;* construct SHC constant. begin w/t _ lsh[t, shc.countShift];* positioning the shift count.t _ t and (shc.maskShiftCount);t _ t or (shc.rmrm);* add control bitsSHC _ t;t _ pat16 _ shiftNoMask;branch[get16Pxit];get16P4:(pat16X) - (pat16End4C);branch[get16P5, ALU>=0];* IN [pat16End3C..pat16End4C) pattern 4* pattern4 returns pseudo ranom numbersnoop;getRandom[];* IN [Spat2EndC..Spat3EndC) (random numbers)RBASE _ rbase[pat16X];branch[get16PXit], pat16 _ t;get16P5:(pat16X) - (pat16End5C);branch[get16P6, ALU>=0];* IN [pat16End4C..pat16End5C) pattern 5* pattern5 returns all zeros alternating w/ all onest and (1c);skpif[alu=0],t_a0;t_a1;branch[get16PXit], pat16 _ t;get16P6:(pat16X) - (pat16End6C);branch[get16PXit, ALU>=0];* IN [pat16End5C..pat16End6C) pattern 6* pattern6 returns all ones alternating w/ all zerost and (1c);skpif[alu#0],t_a0;t_a1;branch[get16PXit], pat16 _ t;get16PXit:link _ Klink;subroutine;return, RBASE_ rbase[defaultRegion];getCur16pattern: subroutine;* return curSPattern in TsaveReturn[Klink];RBASE _ rbase[pat16];t _ pat16;returnUsing[Klink]; gp *;tN bAq ap_q^ ]K+r \q1Y71W^ V[ UpS_ +%P +"O+NiK+JIsH6 EpD}qC@ B+r @q'?>J +,= ; 9Tp8q6 5+r 4^q43 10/h ,p+q*r )4+r 'q4& %|$># p Hq  $ Rpq + \ BNTIfuSubrs.mcJune 18, 1981 9:59 AM%8* April 26, 1979 9:56 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iPat8nextPat8getPat8This code implements an 8 bit pattern generator. It is similar to the other pattern code except thatthere is only one pattern and it is a counter that ranges in [0..400).%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iPat8: subroutine;t _ cm1;return, pat8X _ t;nextPat8: subroutine;RBASE _ rbase[pat8X];t _ pat8X _ (pat8X)+1, RBASE _ rbase[defaultRegion];return, PD _ t-(400C);* ALU=0 when pattern is donegetPat8: subroutine;RBASE _ rbase[pat8X];return, t _ pat8X, RBASE _ rbase[defaultRegion]; gp *;tN bAq aB,h^p+f]+\w Zfqe Y)F WB Upq TS_ QNpq PN4M+ Kpq JGI 0 GD bbIfuSubrs.mcJune 18, 1981 9:59 AM%9* February 1, 1980 7:34 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iIAddrnextIAddrgetIAddrifu address loop control%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iIAddr: subroutine;* initialize Ifu addressest _ cm1;return, IAddrX _ t;nextIAddr: subroutine;* rtns t = next ifu address (ALU#0 =>valid)RBASE _ rbase[IAddrX];t _ IAddrX _ (IAddrX)+1, RBASE _ rbase[defaultRegion];return, t - (IfuEndAddrC);getIAddr: subroutine;* rtns t = current ifu address (ALU#0 =>valid)RBASE _ rbase[IAddrX];return, t _ IAddrX, RBASE _ rbase[defaultRegion];iIAddrDownCtrl: subroutine;t_IfuEndAddrC;return, IAddrX_t;nextIAddrDown: subroutine;RBASE_rbase[IAddrX];t_ IAddrX_ (IAddrX)-1, RBASE_ rbase[defaultRegion];skpif[ALU<0];return, PD_ 1c;return, PD_ 0c;* no more addrs gp *;tN bAq aB,_p+^+f]K Zq YB Wpq +VDU Rp q ++QNP6N LXpq +.KI1 Gbpq F$ D Cp q BlA.3? >=v+@ <>+IfuSubrs.mcJune 18, 1981 9:59 AM%10* July 3, 1979 12:57 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++IFU: EXCEPTION CONDITION ENTRY POINTS.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++top level;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Instruction Set 3: Exception Condition Entry PointsException conditions occur in order of highest priority.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Kfault3:* instruction set 3: Memory faultcall[checkException], t _ exceptions.kfault3,at[0];call[checkException], t _ exceptions.kfault3,at[1];call[checkException], t _ exceptions.kfault3,at[2];branch[checkException], t _ exceptions.kfault3,at[3];FGParity3:* instruction set 3: Parity Error in FG data from memDcall[checkException], t _ exceptions.FGPe3,at[4];call[checkException], t _ exceptions.FGPe3,at[5];call[checkException], t _ exceptions.FGPe3,at[6];branch[checkException], t _ exceptions.FGPe3,at[7];Resched3:* instruction set 3: Want reschedulecall[checkException], t _ exceptions.resched3,at[14];call[checkException], t _ exceptions.resched3,at[15];call[checkException], t _ exceptions.resched3,at[16];branch[checkException], t _ exceptions.resched3,at[17];NotReady3:* instruction set 3: Ifu not yet ready to respond (pipe empty)call[afterdispatch],at[34];call[afterDispatch],at[35];call[afterDispatch],at[36];branch[afterDispatch],at[37];RamPE3:* instruction set 3: Parity Error in Ifu Ramcall[checkException], t _ exceptions.RamPe3,,at[74];call[checkException], t _ exceptions.RamPe3,,at[75];call[checkException], t _ exceptions.RamPe3,,at[76];branch[checkException], t _ exceptions.RamPe3,at[77];%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Instruction Set 2: Exception Condition Entry PointsException conditions occur in order of highest priority.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Kfault2:* instruction set 2: Memory Faultcall[checkException], t _ exceptions.kfault2,at[100];call[checkException], t _ exceptions.kfault2,at[101];call[checkException], t _ exceptions.kfault2,at[102];branch[checkException], t _ exceptions.kfault2,at[103];FGParity2:* instruction set 2: Parity Error in FG data from memDcall[checkException], t _ exceptions.FGPe2,at[104];call[checkException], t _ exceptions.FGPe2,at[105];call[checkException], t _ exceptions.FGPe2,at[106];branch[checkException], t _ exceptions.FGPe2,at[107];Resched2:* instruction set 2: Want reschedulecall[checkException], t _ exceptions.resched2,at[114];call[checkException], t _ exceptions.resched2,at[115];call[checkException], t _ exceptions.resched2,at[116];branch[checkException], t _ exceptions.resched2,at[117];NotReady2:* instruction set 2: Ifu not yet ready to respond (pipe empty)call[afterdispatch],at[134];call[afterDispatch],at[135];call[afterDispatch],at[136];branch[afterDispatch],at[137];RamPE2:* instruction set 2: Parity Error in Ifu Ramcall[checkException], t _ exceptions.RamPe2,at[174];call[checkException], t _ exceptions.RamPe2,at[175];call[checkException], t _ exceptions.RamPe2,at[176]; gp *;tN bAq aB"K_p&q ^B1\ ZBYp4 XUq8 WB Upq"@S--pq@R--@QN--@P/0Z Mpq7@L+-p@Kq+-@JG+-@I -- Fpq%@E.-pq@D}.-@C@.-@B00Z ?pq?@>pq@=v@<8@: 8pq-@7--pq@6o--@51--@3.- 1B/p4 -q8 ,B *rpq"@)4--pq@'--@&--@%|/0Z #jpq7@"-+-p@ q+-@+-@t-- cpq%@&.-pq@.-@.-@m00Z \pq?@pq@@@f Upq-@ ,-pq@ ,-@ ,- 2 y<=]IfuSubrs.mcJune 18, 1981 9:59 AM%11branch[checkException], t _ exceptions.RamPe2,at[177];%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Instruction Set 1: Exception Condition Entry PointsException conditions occur in order of highest priority.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Kfault1:* instruction set 1: Memory Faultcall[checkException], t _ exceptions.kfault1,at[200];call[checkException], t _ exceptions.kfault1,at[201];call[checkException], t _ exceptions.kfault1,at[202];branch[checkException], t _ exceptions.kfault1,at[203];FGParity1:* instruction set 1: Parity Error in FG data from memDcall[checkException], t _ exceptions.FGPe1,at[204];call[checkException], t _ exceptions.FGPe1,at[205];call[checkException], t _ exceptions.FGPe1,at[206];branch[checkException], t _ exceptions.FGPe1,at[207];Resched1:* instruction set 1: Want reschedulecall[checkException], t _ exceptions.resched1,at[214];call[checkException], t _ exceptions.resched1,at[215];call[checkException], t _ exceptions.resched1,at[216];branch[checkException], t _ exceptions.resched1,at[217];NotReady1:* instruction set 1: Ifu not yet ready to respond (pipe empty)call[afterdispatch],at[234];call[afterDispatch],at[235];call[afterDispatch],at[236];branch[afterDispatch],at[237];RamPE1:* instruction set 1: Parity Error in Ifu Ramcall[checkException], t _ exceptions.RamPe1,at[274];call[checkException], t _ exceptions.RamPe1,at[275];call[checkException], t _ exceptions.RamPe1,at[276];branch[checkException], t _ exceptions.RamPe1,at[277];%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Instruction Set 0: Exception Condition Entry PointsException conditions occur in order of highest priority.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Kfault0:* instruction set 0: Memory Faultcall[checkException], t _ exceptions.kfault0,at[300];call[checkException], t _ exceptions.kfault0,at[301];call[checkException], t _ exceptions.kfault0,at[302];branch[checkException], t _ exceptions.kfault0,at[303];FGParity0:* instruction set 0: Parity Error in FG data from memDcall[checkException], t _ exceptions.FGPe0,at[304];call[checkException], t _ exceptions.FGPe0,at[305];call[checkException], t _ exceptions.FGPe0,at[306];branch[checkException], t _ exceptions.FGPe0,at[307];Resched0:* instruction set 0: Want reschedulecall[checkException], t _ exceptions.resched0,at[314];call[checkException], t _ exceptions.resched0,at[315];call[checkException], t _ exceptions.resched0,at[316];branch[checkException], t _ exceptions.resched0,at[317];NotReady0:* instruction set 0: Ifu not yet ready to respond (pipe empty)call[afterdispatch],at[334];call[afterDispatch],at[335];call[afterDispatch],at[336];branch[afterDispatch],at[337];RamPE0:* instruction set 0: Parity Error in Ifu Ramcall[checkException], t _ exceptions.RamPe0,at[374];call[checkException], t _ exceptions.RamPe0,at[375];call[checkException], t _ exceptions.RamPe0,at[376];branch[checkException], t _ exceptions.RamPe0,at[377]; gp *;tN@bAq.- `0B^p4 \q8 ZB Xpq"@W--pq@VD--@U--@S/0Z Qpq7@Pz+-p@O=q+-@M+-@L-- Jpq%@Is.-pq@H6.-@F.-@E00Z Cpq?@Blpq@A.@?@> Y_ XUH VDc Sp0Qq(rqrq&Pz^O=4pqMOrqL\K[JG\ I B Fp'q51EQ-.p1D-.p1B-.p1A-.p @[p q ?p 1=q ;ep'qE1:'" 18" 17" 16o"  51p 13q 1211y .p'qO1-#&1,#&1+E#&1*#& (p 1'q &Op1%q1#, !Ypq'1 &)zpq1&)z1&)z1c &p 1q11m'710 pq'1wpq1:11 Dpq'+1 pq B](OIfuSubrs.mcJune 18, 1981 9:59 AM%13call[afterDispatch],at[65];call[afterDispatch],at[66];branch[afterDispatch],at[67];opIfad16:* successful jumps hereIFUJump[],at[70];IFUJump[],at[71];IFUJump[],at[72];IFUJump[],at[73];opIfad22Err:* pause-halt herebranch[err],at[110];branch[err],at[111];branch[err],at[112];branch[err],at[113]; gp *;tN1bAq1a1_ ]Kpq'1\ pq1Z 1Y 1XU  Up q1T pq1S_ 1R" 1P H OfIfuSubrs.mcJune 18, 1981 9:59 AM%14* June 29, 1979 11:45 AMafterDispatch: subroutine;* come here after ifuNextMacro.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++SOME OTHER routine should set "expectedDispatch" to the absolute value of the locationwhere we expected to dispatch.SET stack+1 to current value of POINTERS, then reset RBASE to defaultRegion. Returnwith stkp at its original value (ie., users must increment stkp to see POINTERS).%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++stkp+1, global;stack&-1_POINTERS;RBASE _ rbase[defaultRegion];* reset Rbase since Ifu causes it to changerscr _ link;* compute where we came fromtop level;afterDispatch2:* enter here from checkExceptiont _ expectedDispatch;* was that where we wanted to go?skpif[ALU>=0], rscr _ (rscr)-1;* link = where we came from +1branch[afterDispRet];* don't check return if expected val<0t#(rscr);skpif[ALU=0], t _ rscr2, RBASE _ rbase[klink];* restore TafterDispErr:breakpoint;* expectedDispatch # rscrafterDispRet:subroutine;link_klink;return, RBASE _ rbase[defaultRegion];* July 3, 1979 1:53 AM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++The various exception conditions (except for notReady) call this subroutine. If the exception thatwas called has been enabled, control proceeds through afterdispatch. Otherwise we stop at abreakpoint.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++KnowRbase[defaultRegion];* depend upon exceptionBit NOT in defaultRegioncheckException: subroutine;exceptionBit _ t, global;stkp+1;stack&-1 _ POINTERS;* where afterDispatch saves POINTERSRBASE _ rbase[defaultRegion];rscr _ link;rscr _ (rscr) -1;top level;RBASE _ rbase[exceptionsMask];t _ exceptionsMask;rscr2 _ t;t _ exceptionBit, RBASE _ rbase[defaultRegion];t and (rscr2);* see if current exception conditionskpif[ALU#0];* has been enabledIfuExceptionErr:* rscr = return link to offending exception conditionerror;* presumably klink = return link to source of ifujump.branch[afterDispatch2], rscr _ (rscr)+1;* reincrement exception since afterdispatch willdecrement it. gp *;tN bAq _p q  ^B \V Z XUT WQ UB@S_@R"@O++@Ni +@M, Jp-q@Is+!@H6+@F+&@E@D}.- C@p @Bq + @p @?q @>J @= % : 9TB 8c 6\ 5 4^B@3 +/ 1pq @0@/h@.*+$@,@+ @*r@)4 @'@&@%| @$>/@# +$@! + p+q5@H+1  @(+0  L COIfuSubrs.mcJune 18, 1981 9:59 AM%15* January 18, 1979 6:47 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++muffler reading routines%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++readMufBit: subroutine;* read a muffler bit. Enter w/ t = address* CLOBBERS T, rscr, rscr2, cnt, stkppushReturn[];subroutine;* don't clobber link w/ transfer of ctrlcnt _ 10s;readMufBitsL:MidasStrobe _ t;noop;noop;loopUntil[cnt=0&-1, ReadMufBitsL], t _ lsh[t, 1];t _ link;returnP[];readMuffler: subroutine;* read a muffler byte and return its value* in T. Enter with T = muffler address. Return 8 successive bits from that address.* CLOBBERS T, rscr, rscr2, cnt, stkppushReturnAndT[];* tos = trscr2 _ t-t;* keep assembled bits in rscr2rscr _ t-t;* rscr = loop countreadMufflerL:rscr2 _ lsh[rscr2, 1];call[readMufBit], t _ stack;* get current bit addressrscr2 _ (rscr2) or t;* add the current bitt _ (stack)+1;* compute address of next bitstack _ t;(rscr)-(10c);* have we accumulated a byte yet?loopUntil[ALU=0, readMufflerL], rscr _ (rscr)+1;t _ rscr2;pReturnP[];* tos-1 = return link gp *;tN bAq aB1_p ^qB ]Kp q * \$Z Y n)XU Up TqS_R"P1NiM, Jp q * IsS H6$ED} nC@ n Bp @q?#&>Jv; : 8 n!604^ 3 nP 176KifuTestSubrs.mcSeptember 17, 1979 6:38 PM%1%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Table of ContentsOrganized by Occurrence of subroutine in this ListingSubroutineFunction+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++initIfuCacheInit memory, IfuMemory and write opcodes into memoryiMemInitialize memory system for IfuifuOpcodesToMemConstruct various "programs" in "main" memoryappendHaltsWrite three halt opcodes into memory using address in CDbyteAddr.getCDbyteAddrReturn t = "current cache byte address"putCDbyteAddrSet "current cache byte address" with tputNextByteWrite byte in T into cache at current addr, then increment the addrputCDbyteWrite byte in rscr into memory byte addr in tgetCDbyteReturns the byte pointed to by TgetIUsingInstrSetReturns current value of iUsingInstrSetsetIUsingInstrSetSets value of iUsingInstrSetfixByteAddrForInstrSetModify a byte address to accommodate the current instr. setResetIfuReset ifu, zero IfuTest, clear reschedPendingifuGetInstrSetReturn the current value of ifu instruction setifuSetInstrSetSet the current value of the ifu instruction set.initItestInitialize the test loop controlinitTestCountInitialize the test opcode countnextITestReturn ALU=0 ==> no more tests, t = memory byte addr of next testgetTestBoundsHIDEOUS IMPLEMENTATION DEPENDENT routine that returns the beginningand end byte address of the "current" IFU test (test indicated by iTestX).getIfuNotReadyLocReturns t=not ready location for current instr set.nextITestCountReturn ALU=0 ==> no more counts, t = current countifuTestLoopinfinite loop that invokes a particular (passed in T) ifu executintest%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++%September 17, 1979 6:37 PMRemove reference to afterIfu3.mcAugust 1, 1979 10:38 AMCause ifuSetInstrSet to set iUsingInstrSet.July 3, 1979 12:02 AMAdd code to handle various exception conditions: Cause initIfuCache to clear exceptionsMask.June 29, 1979 3:35 PMAdd slight performance enhancement to memory initialization loop in iMem, fix bug inFixByteAddrForInstrSet that prevented it from noticing that instruction set 2 accesses the bytes rightto left.June 28, 1979 11:45 AMCall xGetConfig in iMem.June 6, 1979 10:32 AMFix placement problems in getIfuNotReadyLoc.June 5, 1979 11:46 AMAdd call to disableConditionalTask in iMem.June 4, 1979 10:06 AMAdd getIfuNotReadyLoc.May 30, 1979 10:44 AMAdd boiler plate to iMem to withstand effects of power-up sequence on Dorado.May 4, 1979 10:09 AMAdd _ID instructions to ifuTestLoop -- to suck data out of pipe in case of 3 byte instrs.May 2, 1979 10:33 AMAdd calls to ifuGetInstrSet, ifuSetInstrSet to force microD to place them properly (they are Midassubroutines, only, for the moment).May 1, 1979 5:01 PMAdd getIfuInstrSet, setIfuInstrSet.April 27, 1979 4:54 PMFix bug in fixByteAddrForInstrSet.April 26, 1979 5:04 PMCreate this file from ifu3.mc%gp)>zN bAqB(`apH_5^q "  ]K?\p " q4Zp" qYp" q-XUp " qAWp " q'Up " q'Tp " qCS_p" q-R"p" qPp" q'Op" qNip" q;M,p" q-Kp " q/Jp " q1Isp" qH6p " qFp" qAEp " qC D}JC@p" q3Bp " q2@p " qB ? = B : 9T18 615+ 4^13 ] 110T /hf .* ,1+ *r1)4, '1&+ %|1$> #1!M 1HY  1b # R1# 1" \1  v E3VKifuTestSubrs.mcSeptember 17, 1979 6:38 PM%2* July 3, 1979 12:03 AM%initIfuCacheThis code has four main functions:It initializes the Dorado storage systemIt backgrounds all IfuM with valid parity opcodes to a location that invokes error.It writes opcodes into IfuM[21:30]It writes a succession of byte codes into the cache%initIfuCache: subroutine;pushReturn[];t _ a0;exceptionsMask _ t;* disallow all exceptions but "notReady"call[iMem], t _ t-t;* Use col 0 of cache exclusively.call[ifuBackground];* write halts into all locations of the Ifucall[initIfuMemory];* write our opcodes into special locationscall[ifuOpcodesToMem];* write various programs into memoryreturnP[];gp)>zN bAq a_p ^q"]K(\SZ"Y3 XU Wp q U TS_+(R"+!P++O+*Ni+$M,  K<@iifuTestSubrs.mcSeptember 17, 1979 6:38 PM%3* June 28, 1979 11:46 AMiMem: subroutine;* Enter w/ t IN[0..3] ==> use one columnpushreturnAndT[];* of cache (t specifies the column).RBASE _ rbase[MemoryOK];t _ MemoryOK, RBASE _ rbase[defaultRegion];branch[iMemXit, ALU#0];* only do this once* Background storage so that mem[va] = va for first 65 K memory.call[disableConditionalTask];call[xGetConfig];* set up to handle current configuration.t _ FaultInfo'[];* clear any wairting faultscall[clearCacheFlags];* nothing in the cachecall[presetMap];* start up the mapt _ 200c;* use the error correctorcall[setTestSyn];call[clearCacheFlags];* nothing in the map (setting Tsyn changed cache)t _ 37C;* init ifu's membasecall[setMbase];rscr _ t-t;call[setBR], rscr2 _ t-t;* Use zero in Ifu's base registerMEMBX_0s;* We'll use membase zero, and zero it, too.call[setMbase], t _ t-t;rscr_ t-t;call[setBR], rscr2 _ t-t;(stack) - (4c);* see if we're supposed to use only one colskpif[ALU<0];* of the cahcebranch[iMemSetMcr], t _ r0;t _ lsh[stack, 13];* sigh. we can't fit memdefs, sot _ t or (b2);* use numbers. should be mcr.useMcrViMemSetMcr:t _ t or (b14);* should be mcr.noSEwake;stack+1 _ t;* remember it for a whilecall[setMCR], t _ t or (b15);* should be mcr.noWaket _ rscr _ A0;iMemWriteL:* tight loop that writes all of storagePreFetch _ rscr;* Prefetch is uninteresting first time thru.cnt _ 17s;loopUntil[CNT=0&-1, .], t _ (STORE_t)+1, DBuf_t;* write current munchloopUntil[ALU=0, iMemWriteL], rscr _ t + (40C);* increment prefetch pointert _ rscr _ 100000C;* do it again, just to make sure we flushiMemWriteL2:* the cache. Otherwise, there may stillPrefetch _ rscr;* be storage with bad parity.cnt _ 17s;loopUntil[CNT=0&-1, .], t _ (STORE_t)+1, DBuf_t;loopUntil[ALU=0, iMemWriteL2], rscr _ t + (40c);t _ 1c;* remember that we've done all this;MemoryOK _ t;B _ FaultInfo'[];call[setMCR], t _ stack&-1;* set MCR for default value.iMemXit:pReturnP[];gp)>zN bAq apq +(_+$^]K+\+Z@XUW+)U+T+S_+R"+PO+1Ni+M,K J+!H6++FE D}B++@ + ?>J+= +$ ;p :q+9T +8+6 5p +q'4^+,3 100Z0/0Z.*+) ,p +q(++*r )40'0&+$%| #!+ Hp q  @KaifuTestSubrs.mcSeptember 17, 1979 6:38 PM%4* January 22, 1979 8:31 PM%ifuOpcodesToMem -- write opcodes into cache: FOR INSTRUCTION SETS 2, 3This initialization works ONLY for instruction sets two and three -- those insrtuction sets take datafrom the right half FIRST, then the left half of the word. PutNextByte ALWAYS works left to right.word 0 byte 0(test0MemByteLocC)begins one byte jump .word 30byte 60(test1MemByteLocC)begins two byte jump .word 50byte 120(test2MemByteLocC)begins (two byte) jump .+2, jump .-2word 100byte 200(test3MemByteLocC)a small program whose opcodes cross word boundaries.word 200byte 400(---------)fastTest code (not appropriate to "default" tests.%ifuOpcodesToMem: subroutine;pushReturn[];call[setIUsingInstrSet], t _ 3c;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Background all storagte with "identity".%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++t _ cm1;cnt _ t;t _ t-t;loopUntil[cnt=0&-1, .], t _ (store_t)+1, DBuf _ t;%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Write one-byte "jump ." into LOCATION 0, followed by "halts".Logical:(jump. fastHalt) (fastHalt fastHalt) (fastHalt fastHalt) (fastHalt )Physical:(fastHalt jump.) (fastHalt fastHalt) (fastHalt fastHalt) (fastHalt )%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iic3:* write jump0 into the first 40B bytes in the cache* At word 0, byte 0call[putCDbyteAddr], t_test0MemByteLocC;* begin writing at location zerocall[putNextByte], t _ jump0;call[putNextByte], t _ fastHalt;call[appendHalts];* try to keep ifu from deep-ending%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++Write two-byte "jump ." into word LOCATION 30, followed by "halts".Logical:(jump+ 0) (fastHalt fastHalt) (fastHalt fastHalt) (fastHalt fastHalt)Physical:(0 jump+) (fastHalt fastHalt) (fastHalt fastHalt) (fastHalt fastHalt)%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iic4:* place a two byte jump . into cache.* at word location 30t_test1MemByteLocC;call[putCDbyteAddr];* initialize the byte addresscall[putNextByte], t _ jumpL2;* put the offset (=0)call[putNextByte], t _ r0;* put the opcode (=2byte jump)call[appendHalts];* try to keep ifu from deep-ending%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++At word LOCATION 50, byte LOCATION 100 (test2MemByteLocC):Logical:(jumpL2 2) (jumpML2- -2)(fastHalt fastHalt) (fastHalt fastHalt) (fastHalt fastHalt)Physical:(2 jumpL2) (-2 jumpML2)(fastHalt fastHalt) (fastHalt fastHalt) (fastHalt fastHalt)%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iic5:* place an infinite loop into the cache: jump .+2, jump .-2, where opcode len=2.t _ test2MemByteLocC;call[putCDbyteAddr];gp)>zN bAq a_pqp ^qe ]Kc Z``+ Y``+ XU``+$ W``+4 U`` (2 T R"pq P O NiB M,( KBJIsH6F2 EB C@p q B1@S ?1>JS = D ;p'q3 :18()z1514^13 " 0B .*"p q ,1+E *r1)4E 'B %|pq% $>1!1 1 $1" 1" B p q' \1S 1R fB pqQ1 1 p D]/ifuTestSubrs.mcSeptember 17, 1979 6:38 PM%5call[putNextByte], t _ jumpL2;call[putNextByte], t _ 2c;call[putNextByte], t _ jumpML2;call[putNextByte], t _ cm2;* now jump .-2call[appendHalts];* try to keep ifu from deep-endingiic6:%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++At word LOCATION 100, byte location 200 (test3MemByteLocC):Logical:(op1 op2)(A op3)(A B)(jumpML2 6)(fastHalt fastHalt)(fastHalt fastHalt)(fastHalt fastHalt)Physical (extracting right to left from memory):(op2 op1)(op3 A1=2)(B2=32 A2=31)(-6 jumpML2)(fastHalt fastHalt)(fastHalt fastHalt)(fastHaltfastHalt)%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++t _ test3MemByteLocC;call[putCDbyteAddr];noop;* for placementcall[putNextByte], t _opNoop ;* cross word boundary on 2 byte instr.call[putNextByte], t _ opNoopL2;call[putNextByte], t _ 2c;call[putNextByte], t _ opNoopL3;* cross word boundary on 3 byte instr.call[putNextByte], t _ 31c;call[putNextByte], t _ 32c;call[putNextByte], t _ JumpML2;call[putNextByte], t _ (add[not[6],1]C);* offset for jumpML2 is -6call[appendHalts];* try to keep ifu from deep-ending%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++At word LOCATION 200, byte location 400:Logical:(fastExit fastFetch) (fastStore fast1) (fastFetch fastStore) (fastJfail toHalt) (fastJ top3)(fastHalt fastJ)(-11d fastHalt) Physical (extracting right to left from memory):(fastFetch fastExit) (fast1 fastStore) (fastStore fastFetch) (toHalt fastJfail) (top3 fastJ)(fastMJ fastHalt)(fastHalt -11d) %*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++iic7:t _ (lshift[200,1]C);* begin at word 200call[putCDbyteAddr];noop;* for placementcall[putNextByte], t _ fastExit;call[putNextByte], t _ fastFetch;call[putNextByte], t _ fastStore;call[putNextByte], t _ fast1;call[putNextByte], t _ fastFetch;call[putNextByte], t _ fastStore;call[putNextByte], t _ fastJfail;call[putNextByte], t _ 10c;call[putNextByte], t _ fastJ;call[putNextByte], t _ 3c;call[putNextByte], t _ fastHalt;call[putNextByte], t _ fastMJ;noop;* for placement.call[putNextByte], t _ (add[not[13],1]C);call[putNextByte], t _ fastHalt;* -11d = -13B = not(13B)+1call[putNextByte], t _ fastHalt;* try to keep ifu from deep-endingcall[appendHalts];call[appendHalts];t _ 100c;call[longWait];* assure that the ifu's mem refs won't missreturnP[];appendHalts: subroutine;pushReturn[];call[putNextByte], t _ fastHalt;call[putNextByte], t _ fastHalt;gp)>zN1bAq1a1_1^" 1\" Yp XUqD Wpqp q' U1TY S_11R"[ P OBLKaJ#+H+&GFkE-+&CBAu@7(+1>" =B ;Ap q :18\ 7/ 6K115\ 30 2B /p.Mq+-++*)W!(!&%!$a!#$!! k.+u)8++"B++ p q    V 3@])ifuTestSubrs.mcSeptember 17, 1979 6:38 PM%6call[putNextByte], t _ fastHalt;returnP[];gp)>zNbAqa V _"hifuTestSubrs.mcSeptember 17, 1979 6:38 PM%7* April 26, 1979 9:00 AM%These subroutines support writing opcodes into the cache. Note that several ofthem use and increment the "current" byte address in the cache:getCDbyteAddrreturns t = "current" cache byte addresssetCDbyteAddrt = new value for "current" cache byte addressputNextBytet = byte. place t into "current" cache byte location, increment current addrputCDbytet = byte address, rscr = value. Put rscr into indicated byte addressgetCDbytet = byte address, Returns T = byte at that byte locationsetIUsingInstrSett = instr set number. set iUsingInstrSetgetIUsingInstrSetReturns t = current instruciton set numberfixByteAddrForInstrSett = byte address, returns t = byte address modified toreference a byte for the current instruction set. Don't clobber rscr!%getCDbyteAddr: subroutine;RBASE _ rbase[currentCDbyte];t _ currentCDbyte, RBASE_rbase[defaultRegion];return;putCDbyteAddr: subroutine;RBASE _ rbase[currentCDbyte];currentCDbyte _ t, RBASE _ rbase[defaultRegion];return;putNextByte: subroutine;* enter w/ t = byte to put in "current"noop, global;pushReturnAndT[];* location in cache. Increment thet _ stack;* current address after writing the byterscr _ t;* save the byte to writecall[getCDbyteAddr];call[putCDbyte];* write itcall[getCDbyteAddr];* increment the current addresscall[putCDbyteAddr], t _ t+1;pReturnP[];putCDbyte: subroutine;* t = byte address, rscr = byte valuepushReturn[];* use stack, clobber rscr, t.call[fixByteAddrForInstrSet];* modify byte address if requiredstack+1 _ t;* save it on the stackt _ stack;t and (1c);* see if odd bytebranch[putCDbyteOdd, ALU#0];* put it into left sidet _ t rsh 1;* fetch the current 16bit valueFETCH _ t;t _ MD;rscr _ lsh[rscr, 10];* position the byte to the left sidet _ t and (377C);* keep the current right side of memoryrscr _ t or (rscr);* Rscr = the new 16 bit value.t _ (stack) rsh 1;* retrieve memory byte pointerSTORE _ t, DBuf _ rscr;branch[putCDxit];putCDbyteOdd:* odd byte address ==> right half of wordt _ t rsh 1;* fetch the current 16bit valueFETCH _ t;t _ MD;rscr _ (rscr) and (377c);* isolate the bits on the right sidet _ t and (177400C);* keep the current left siderscr _ (rscr) or t;* Rscr = the new 16 bit value.t _ (stack) rsh 1;* retrieve memory byte pointerSTORE _ t, DBuf _ rscr;putCDxit:pReturnP[];gp)>zN bAq a _O ^? \p  q( Zp  q. XUp  qL Wp qD Up q8 Tp q( S_p q* R"p+q6 PF O M,p q KJ.Is H6p q FE0D} Bp q +'@ ?+#>J +(;+:9T+ 6+54^ 1pq +%0 +/h+!.* +, + +*r )4p'q +& %|#+$!+' + + p +q) + \+$+f+ +  pp 3q & D]CifuTestSubrs.mcSeptember 17, 1979 6:38 PM%8getCDbyte:* enter w/ t = byte addresspushReturn[];call[fixByteAddrForInstrSet];* modify byte address if requiredrscr _ t;branch[getCDodd, r odd], rscr _ (rscr) rsh 1;FETCH _ rscr;t _ MD;t _ rsh[t, 10];getCDbyteRtn:returnP[];getCDodd:FETCH _ t;t _ MD;branch[getCDbyteRtn], t _ t and (377C);* June 29, 1979 3:35 PM%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++When we use instruction set 2 or 3, the ifu fetches bytes in the inverse order. Ie., Loc 0 impliesthe right byte of word 0 and loc 1 implies the left byte of word 0. This terrible hack accommodatesthe Alto's Mesa implementation which addresses bytes in this way.For the duration, all instruction sets invert the bytes.%*++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++setIUsingInstrSet: subroutine;return, iUsingInstrSet _ t;getIUsingInstrSet:RBASE _ rbase[iUsingInstrSet];return, t _ iUsingInstrSet, RBASE _ rbase[defaultRegion];fixByteAddrForInstrSet:pushReturnAndT[];call[getIUsingInstrSet];t-(2c);* invert the order of the bytes if weskpif[ALU>=0];* are using instr set 3 or 4.branch[fbaifiRtn], t _ (stack&-1);* rtn w/ t = original input, adjust stackbranch[fbaifiOdd, R ODD], t _ (stack&-1);* put byte addr back into t, adjust stackbranch[fbaifiRtn], t _ t + 1;* it is an even byte addressfbaifiOdd:* address is odd, IN instructionSet2 or 3.t _ t and (177776C);* remove low order bitfbaifiRtn:returnP[];gp)>zN a +q_ ^+!]K\-Z YXU Wp Uq S_pR"q PO' M, KB Jc Isd H6A Fp8 EqB D}pq C@ Bp@q?9 >Jp= q:9T+%8 +6"+)4^)+)3 + 1p +q*0+ /hp .*q  ,C;AifuTestSubrs.mcSeptember 17, 1979 6:38 PM%9* August 1, 1979 10:40 AM%ResetIfuReset the Ifu by performing two IfuReset functions separated by a longWait of 100B cycles.%resetIfu: subroutine;pushReturn[];t _ t-t;ifuTest_t;IfuReset[];noReschedule[];call[longWait], t _ 100c;ifuReset[];returnP[];* May 2, 1979 10:32 AMtop level;call[ifuGetInstrSet];* These two subroutine calls force microDcall[ifuSetInstrSet];* to place the subroutine entry pts properly.noop;ifuGetInstrSet: subroutine;t_ not(IFUMLH');return, t _ ldf[t, ifu.InstrSetSize, ifu.GetInstrSetShift];ifuSetInstrSet: subroutine;t _ t and (ifu.InstrSetMask);iUsingInstrSet _ t;t _ lsh[t, ifu.SetInstrSetShift];t _ t or (100000C);return, MOS _ t;gp)>zN bAq a+f_p ^qZ ]K \pq Z YXU W UTS_ R" ONi M,+)K+-J Isp q H6F; D}pq C@B@!?>J <>%+"ifuTestSubrs.mcSeptember 17, 1979 6:38 PM%10* April 24, 1979 8:12 AM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++test iteration control:initItestinitTestCountnextTestgetTestBoundsnextTestCountThese subroutines cause the main ifu diagnostic to iterate a fixed number of times for each test, thento change to the next test.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++initItest: subroutine;t_cm1;return, iTestX_t;initITestCount:t _ cm1;return, iTestCountX_t;nextITest: subroutine;* RTN: ALU#0 ==> more tests to do;pushReturn[];* T = memory byte location of current test.RBASE _ rbase[iTestX];t _ iTestX _ (iTestX)+1, RBASE _ rbase[defaultRegion];t # (lastTestC);branch[nextITestXDone, ALU=0];Bdispatch _ t;branch[testMemTable];set[testMemTbl, 1140];testMemTable:branch[nextITest2], t _ test0MemByteLocC,at[testMemTbl,0];branch[nextITest2], t _ test1MemByteLocC,at[testMemTbl,1];branch[nextITest2], t _ test2MemByteLocC,at[testMemTbl,2];branch[nextITest2], t _ test3MemByteLocC,at[testMemTbl,3];nextITest2:iCurrentTestLoc _ t;rscr _ 1c;nextITestXit:returnPandBranch[rscr];nextITestXDone:branch[nextITestXit], rscr _ t-t;%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getTestBoundsHIDEOUS DEPENDENCY:THIS CODE PRESUMES TO KNOW THE LENGTH OF THE PROGRAMS WRITTEN IN MEMRYRETURNS RSCR = beginning of the current test program in memory (byte location)RSCR2 = end of current test program in memory (byte location)%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getTestBounds:pushReturn[];RBASE _ rbase[iTestX];t_iTestX, RBASE _ rbase[defaultRegion];BDispatch_t;branch[testMemTable2];set[testMemTbl2, 1150];testMemTable2:* this table sets RSCR = lower boundbranch[gtbl0], rscr _ test0MemByteLocC,at[testMemTbl2,0];branch[gtbl1], rscr _ test1MemByteLocC,at[testMemTbl2,1];branch[gtbl2], rscr _ test2MemByteLocC,at[testMemTbl2,2];branch[gtbl3], rscr _ test3MemByteLocC,at[testMemTbl2,3];*This code sets RSCR2 = the upper boundgtbl0: branch[gtblRtn], rscr2 _ rscr;gtbl1: branch[gtblRtn], rscr2 _ rscr;gtbl2: rscr2 _ rscr;branch[gtblRtn], rscr2 _ (rscr2) + (2c);gtbl3: rscr2 _ rscr;rscr2 _ (rscr2) + (6c);gtblRtn:returnP[];%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++gp)>zN bAq a?&\_pq+^p)]K +f\)Z )Y XUqf W U? Tp q S_R" PpOqNi Kp q +#J ++IsH66FED} C@ B @p ?q)+>J)+= )+;)+ :p 9Tq8 6p 5q 4^p3 q! 0?)/hp .*,F +qN*r= )4? 'p &q %|$>'# ! p q Hp +q$ '+p q'+p q'+p qR'+p q & pq \pq pq ( pq f p q 3? E3]FifuTestSubrs.mcSeptember 17, 1979 6:38 PM%11nextTestCountThis subroutine determines if the current test has executed enough times to go on to the next test.ALU#0 means there are more ifuJumps to come.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++nextITestCount: subroutine;pushReturn[];RBASE _ rbase[iTestCountX];t _ iCurrentTestLoc;rscr2 _ t;t _ iTestCountX _ (iTestCountX)+1, RBASE _ rbase[defaultRegion];t # (lastTestCountC);skpif[ALU#0], rscr _ 1c;rscr _ t-t;t _ rscr2;returnPandBranch[rscr];gp)>zN)bA aqc _, ^? ]Kpq 1\ 1Z1Y1XU 1W@1U1T1S_ 1R" 1P OCPifuTestSubrs.mcSeptember 17, 1979 6:38 PM%12* June 6, 1979 10:32 AM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getIfuNotReadyLocReturns T = absolute IM location for the not-Ready dispatch for the current instruction set.ClobberT.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++getIfuNotReadyLoc:pushReturn[];call[ifuGetInstrSet];* return instr set number in tPD_t, stkp+1;* instruction set 0?branch[getReady'Ret, ALU=0], stack _ 334C;t # (1c);* instruction set 1?skpif[ALU#0];branch[getReady'Ret], stack _ 234c;t # (2c);* instruction set 2?skpif[ALU#0];branch[getReady'Ret], stack _ 134c;* it's instr set 2stack _ 34c;* default = instr set 3getReady'Ret:t _ stack&-1;returnP[];gp)>zN bAq _?(`^p ]Kq\J \ Z? YpXUq W+T +S_*P+O Ni#K+J Is#+H6 + Fp qE D}  CD/$vifuTestSubrs.mcSeptember 17, 1979 6:38 PM%13* May 4, 1979 10:07 AM%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuTestLoopThis code implements an infinite loop associated with one of the various ifu execution tests. If allgoes well, control will pass from the location of the IfuJump to after Dispatch to the location thatperfroms the ifuJump (again). In the event a random transfer of control occurs, the place in IM wherecontrol passes must be patched to the location "ifuTestL" which will reset PcF. Note that we suck 4IDs from Ifu -- to free pipe in case of 3 byte instructions w/ encoded constant, packed alpha, etc.%*+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ifuTestLoop:top level;t _ t-1;* enter w/ t = index of ifu testiTestX _ t;call[initIfuCache];call[setIUsingInstrSet], t _ 3c;call[nextItest];skpif[ALU#0];ifuTestLErr:* entered with a bad value in Terror;stack+1 _ t;* remember the byte location in the stack.ifuTestL:call[resetIfu];PcF _ stack;call[setIfuTestLRet];ifuTestLRet:A_ID;A_ID;A_ID;IfuJump[0], A_ID;setIfuTestLRet:pushReturn[];call[sitlr2];t _ link;klink _ t;returnP[];sitlr2:coreturn;branch[ifuTestLRet];gp)>zN bAq a?*d_p ^qe ]Kd \f Z1pq- Yc XU? Wp q1U 1T1S_ 1R"1P1O1Ni M,p q1K1J * Isp1H6q1F 1E D}p 1C@q1B1@1? = p1;q 1: 19T18 16 5p14^q13  1E36KGACHAGACHAGACHA u%')+I/68?B GMOuRX]bdioovuv{q -0 B`$oO 9"~&+139; DG=L R%W_elntkxoz\>*<V    y r$u,46<V@HKQY`bi@mzpwz}Nvo.pX[ MesaDebugger.[pX Mesa6BFS.DF.[[Mesa.Typescript.[[ Mesa.symbols.[[ Mesa.signals. [[B4 Mesa.midas. hi[ 8Mesa.MB.ÔÔC)\ )&Ô E-~E\-# \"Ô Ô:`\')&\)"XEÔ-~F;\4\4\:!kEE !J\HFE\H \H*pEE}B "P\V#$E* [EiR /Bf]c~ Connect To: iT9SB"9J" j/^IfuDiagnostics.Pressmcdanielw22-Jun-81 8:28:52 PDT