1 package com.sun.vlsi.chips.marina.test;
2 /* -*- tab-width: 4 -*- */
3 import java.util.ArrayList;
6 import com.sun.async.test.BitVector;
7 import com.sun.async.test.ChainControl;
8 import com.sun.async.test.ChainTest;
9 import com.sun.async.test.ChipModel;
10 import com.sun.async.test.HP34401A;
11 import com.sun.async.test.Infrastructure;
12 import com.sun.async.test.JtagTester;
13 import com.sun.async.test.ManualPowerChannel;
14 import com.sun.async.test.NanosimModel;
15 import com.sun.async.test.Netscan4;
16 import com.sun.async.test.PowerChannel;
17 import com.sun.async.test.Pst3202Channel;
18 import com.sun.async.test.SiliconChip;
19 import com.sun.async.test.SimulationModel;
20 import com.sun.async.test.VoltageReadable;
21 import com.sun.vlsi.chips.marina.test.Marina.Ilc;
22 import com.sun.vlsi.chips.marina.test.MarinaUtils.CmdArgs;
23 import com.sun.vlsi.chips.marina.test.MarinaUtils.Station;
24 import com.sun.vlsi.chips.marina.test.MarinaUtils.CmdArgs.Mode;
26 import edu.berkeley.fleet.api.Dock;
27 import edu.berkeley.fleet.api.Instruction;
28 import edu.berkeley.fleet.api.Predicate;
29 import edu.berkeley.fleet.api.Instruction.Set.SetDest;
30 import edu.berkeley.fleet.api.Instruction.Set.SetSource;
35 public class MarinaTest {
36 //-------------------------- constants -----------------------------------
37 public static final boolean NEW = true;
38 private static final String SCAN_CHAIN = false ? "marinaNew.xml" : "marina.xml";
39 private static final String NET_LIST = false ? "marinaNew.spi" : "marina.spi";
41 public static final int INSTR_SZ = 36;
43 public static final Dock DOCK = InstructionStopper.DOCK;
44 public static final Instruction.Set.FlagFunction CLEAR_FLAG
45 = Instruction.Set.FlagFunction.ZERO;
46 public static final Instruction.Set.FlagFunction SET_FLAG
47 = Instruction.Set.FlagFunction.ZERO.add(Predicate.FlagA)
48 .add(Predicate.NotFlagA);
49 public static final Instruction.Set.FlagFunction A_FLAG
50 = Instruction.Set.FlagFunction.ZERO.add(Predicate.FlagA);
52 public static final Instruction.Set.FlagFunction B_FLAG
53 = Instruction.Set.FlagFunction.ZERO.add(Predicate.FlagB);
55 // COLUMN_LATENCY is a delay that is larger than the latency through an Infinity column
56 private static final int COLUMN_LATENCY = 10; // nanoseconds
59 // Officially, this should be the number of requeueing no-ops that
60 // can be inserted into an idle dock whose OLC is nonzero.
62 // Less formally, this is roughly the number of stages of
63 // buffering between the instruction insertion point and the
64 // instruction ring, plus the capacity of the instruction ring.
65 private static final int INSTRUCTION_IN_SATURATION_AMOUNT = 19;
67 // This is some number which is significantly greater than
68 // INSTRUCTION_IN_SATURATION_AMOUNT. Increasing it may slow the tests down, but
69 // will never cause them to operate incorrectly.
70 private static final int MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT = 25;
72 // Officially, this should be the number of data items which can
73 // be sent from the dock while the "data" proper stopper is in
74 // the "stopped" state
76 // Less formally, this is roughly the number of stages of
77 // buffering between the dock's data successor and the "data"
80 FIXME: what is the correct value here?
81 private static final int DATA_OUT_SATURATION_AMOUNT = XXX;
84 // This is some number which is significantly greater than
85 // DATA_OUT_SATURATION_AMOUNT. Increasing it may slow the tests down, but
86 // will never cause them to operate incorrectly.
87 private static final int MORE_THAN_DATA_OUT_SATURATION_AMOUNT = 16;
89 // Nominal cycle time assuming 4 GHz throughput
90 private static final double CYCLE_TIME_NS = 0.250;
92 //-------------------------------- types ---------------------------------
94 //-------------------------- private data --------------------------------
95 private static long startTime;
97 private Indenter indenter = new Indenter();
98 private Marina marina;
99 private ChipModel model;
100 private ChainControl cc;
101 private JtagTester tester;
102 private CmdArgs cmdArgs;
103 private PowerChannel corePowerSupply, padsPowerSupply;
104 private VoltageReadable coreVoltmeter, voltmeterForCurrent;
106 //-------------------------- private methods -----------------------------
107 /** @return true if simulation. Return false if we're testing silicon. */
108 private boolean sim() {return model instanceof SimulationModel;}
110 private void prln(String msg) {indenter.prln(msg);}
111 private void pr(String msg) {indenter.pr(msg);}
112 private void adjustIndent(int n) {indenter.adjustIndent(n);}
114 private static void fatal(boolean pred, String msg) {
116 System.out.println("Test Failed");
118 Infrastructure.fatal(msg);
121 private static void printTestTime() {
122 long endTime = System.currentTimeMillis();
123 System.out.println("Test took: "+(endTime-startTime)/1000.0+" sec");
126 // Tell user what we're about to do
127 private static void reportTask(CmdArgs args) {
128 System.out.println("Begin testing Marina");
130 case WHOLE_CHIP_SCHEMATIC_PARASITICS:
131 System.out.println(" Simulate whole chip, schematic parasitics");
133 case WHOLE_CHIP_LAYOUT_PARASITICS:
134 System.out.println(" Simulate whole chip, layout parasitics");
137 System.out.println(" Test silicon");
140 fatal(true, "unrecognized CmdArgs.Mode");
144 private void setUpSuppliesAndMeters(Station station) {
145 // set up power supplies and meters
147 prln("Testing station: "+station);
148 Infrastructure.gpibControllers = new int[] {0};
149 switch (cmdArgs.station) {
151 corePowerSupply = new Pst3202Channel("ch1", "HPST3202", 1);
152 padsPowerSupply = new Pst3202Channel("ch2", "HPST3202", 2);
155 corePowerSupply = new Pst3202Channel("ch1", "HPST3202B", 1);
156 padsPowerSupply = new Pst3202Channel("ch2", "HPST3202B", 2);
159 fatal(true, "Unrecognized station: "+cmdArgs.station);
161 corePowerSupply.setCurrent((float)1.7);
162 corePowerSupply.setVoltageWait((float)1.0);
164 padsPowerSupply.setCurrent((float)0.100);
165 padsPowerSupply.setVoltageWait((float)1.8);
167 coreVoltmeter = new HP34401A(station.coreVoltmeter);
168 voltmeterForCurrent = new HP34401A(station.currentVoltmenter);
172 private MarinaTest(String[] args) {
173 cmdArgs = new MarinaUtils.CmdArgs(args);
175 boolean sim = cmdArgs.mode != Mode.TEST_SILICON;
177 model = new NanosimModel();
178 tester = ((SimulationModel)model).createJtagTester("TCK", "TMS", "TRSTb", "TDI", "TDO");
180 model = new SiliconChip();
181 String ip = cmdArgs.station.ipAddr;
182 tester = new Netscan4(ip, cmdArgs.station.jtagChannel);
184 tester.printInfo = false;
185 int khz = sim ? 1000000 : 1000;
188 switch (cmdArgs.mode) {
189 case WHOLE_CHIP_SCHEMATIC_PARASITICS:
190 netListName = NET_LIST;
191 cc = new ChainControl(SCAN_CHAIN, tester, 1.8f, khz);
192 marina = new Marina(cc, model, indenter);
194 case WHOLE_CHIP_LAYOUT_PARASITICS:
195 netListName = "marina_pads_guts.spi";
196 cc = new ChainControl("???", tester, 1.8f, khz);
200 netListName = "marina_pads_guts.spi";
201 cc = new ChainControl("???", tester, 1.8f, khz);
205 fatal(true, "unrecognized CmdArgs.Mode");
208 cc.noTestSeverity = Infrastructure.SEVERITY_NOMESSAGE;
210 PowerChannel pc = new ManualPowerChannel("pc", false);
211 ChainTest ct = new ChainTest(cc, pc);
213 setUpSuppliesAndMeters(cmdArgs.station);
215 if (sim) ((SimulationModel)model).start("nanosim -c cfg", netListName, 0, true);
216 ct.testAllChains("marina", Infrastructure.SEVERITY_WARNING);
218 doOneTest(cmdArgs.testNum);
220 if (sim) ((SimulationModel)model).finish();
223 /** In the absence of looping, the longest path through Infinity is 4 column delays */
224 private void waitUntilQuiescent() {
225 model.waitNS(4*COLUMN_LATENCY);
228 private double readCurrent() {
229 return voltmeterForCurrent.readVoltage() / cmdArgs.station.ammeterShuntResistance;
232 /** Generate List of BitVectors where Token=true, high 25 data bits
233 * are alternating ones and zeros, low 12 data bits increment from
234 * zero, and address is given by addr. */
235 private List<BitVector> makeIncrDataConstAdr(int num, int addr) {
236 List<BitVector> ans = new ArrayList<BitVector>();
237 BitVector dHi = new BitVector(25, "dataHi");
238 BitVector dLo = new BitVector(12, "dataLo");
239 BitVector t = new BitVector("1", "token");
240 BitVector a = new BitVector(14, "addr");
241 dHi.setFromLong(0x00aaaaa);
243 for (int i=0; i<num; i++) {
245 ans.add(dHi.cat(dLo).cat(t).cat(a));
250 private void stopToStop(ProperStopper s1, ProperStopper s2,
252 List<BitVector> din) {
253 prln("Begin stopToStop");
258 long ctrStart = ctr==null ? 0 : ctr.getCount();
261 waitUntilQuiescent();
263 List<BitVector> dout = s2.drainMany();
265 MarinaUtils.compareItemsOrdered(din, dout);
268 long ctrEnd = ctr.getCount();
269 long delta = ctrEnd - ctrStart;
270 long expect = din.size();
272 "counter delta wrong: expected delta: "+expect+
273 " counter before:"+ctrStart+" counter after:"+ctrEnd);
277 prln("End stopToStop");
279 /** Burst data from src to dst. gate is stopped while loading src. gate
280 * is then run to allow the burst to flow. */
281 private void stopToStopBurst(ProperStopper src, ProperStopper gate,
284 List<BitVector> din) {
285 prln("Begin stopToStopBurst test");
291 long ctrStart = ctr==null ? 0 : ctr.getCount();
294 waitUntilQuiescent();
296 // open the gate to start the burst
298 waitUntilQuiescent();
300 List<BitVector> dout = dst.drainMany();
302 MarinaUtils.compareItemsOrdered(din, dout);
305 long ctrEnd = ctr.getCount();
306 long delta = ctrEnd - ctrStart;
308 long expectA = din.size();
309 fatal(delta!=expectA,
310 "counter delta wrong: expected delta: "+expectA+
311 " counter before:"+ctrStart+" counter after:"+ctrEnd);
315 prln("End stopToStopBurst test");
318 private void stopToStopOne(ProperStopper s1, ProperStopper s2,
319 Counter ctr, int adr) {
320 prln("Begin stopToStopOne");
323 List<BitVector> din = makeIncrDataConstAdr(1, adr);
324 stopToStop(s1, s2, ctr, din);
327 prln("End stopToStopOne");
330 private void stopToStopThree(ProperStopper s1, ProperStopper s2,
331 Counter ctr, int adr) {
332 prln("Begin stopToStopOne");
335 List<BitVector> din = makeIncrDataConstAdr(3, adr);
336 stopToStop(s1, s2, ctr, din);
339 prln("End stopToStopOne");
342 private int indexOf(BitVector o, List<BitVector> dIn) {
343 for (int i=0; i<dIn.size(); i++) {
344 if (o.equals(dIn.get(i))) return i;
348 private String ringDump(List<BitVector> dIn, List<BitVector> dOut) {
349 StringBuffer sb = new StringBuffer();
350 sb.append(" ring dump: ");
351 for (BitVector o : dOut) {
352 sb.append(indexOf(o, dIn)+" ");
354 return sb.toString();
357 private int[][] makeIntArray2D(int a, int b) {
358 int[][] ans = new int[a][];
359 for (int i=0; i<a; i++) ans[i] = new int[b];
363 //=========================================================================
364 // Put top level tests here
365 private void stopToStopOneItem(Marina marina) {
366 stopToStopOne(marina.data, marina.tokOut, null, -1);
368 private void stopToStopThreeItems(Marina marina) {
369 stopToStopThree(marina.data, marina.tokOut, null, -1);
371 private void sendInstructions(Marina marina) {
372 prln("Begin sendInstructions");
375 List<BitVector> din = new ArrayList<BitVector>();
377 BitVector count = new BitVector(36,"count");
378 BitVector one = new BitVector(36, "one");
379 count.setFromLong(0);
381 for (int i=0; i<3; i++) {
383 count = count.add(one);
386 marina.instrIn.fillMany(din);
389 prln("End sendInstructions");
392 private void sendToken(Marina marina) {
393 prln("Begin sendToken");
398 new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, 1));
400 getCtrsFlags(marina);
404 new Instruction.Move(DOCK,
405 false, /* requeueing */
406 Predicate.IgnoreOLC, /* predicate */
407 false, /* torpedoable */
411 false, /* latchData */
412 false, /* latchPath */
417 getCtrsFlags(marina);
419 List<BitVector> toks = marina.tokOut.drainMany();
420 fatal(toks.size()!=1, "Expected one token to emerge but got: "+toks.size()+" tokens");
422 prln("Token="+MarinaUtils.formatDataTokAddr(toks.get(0)));
425 prln("End sendToken");
428 private void sendData(Marina marina) {
429 prln("Begin sendData");
434 new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, 1));
436 getCtrsFlags(marina);
440 new Instruction.Move(DOCK,
441 false, /* requeueing */
442 Predicate.IgnoreOLC, /* predicate */
443 false, /* torpedoable */
447 false, /* latchData */
448 false, /* latchPath */
453 getCtrsFlags(marina);
455 List<BitVector> dataItems = marina.data.drainMany();
456 fatal(dataItems.size()!=1, "Expected one data item to emerge but got: "+dataItems.size()+" data items");
458 prln("Datum="+MarinaUtils.formatDataTokAddr(dataItems.get(0)));
461 prln("End sendData");
464 private void testFlagZ(Marina marina) {
465 prln("Begin testFlagZ");
468 List<BitVector> toks;
470 Predicate only_if_olc_zero = Predicate.OLCZero;
471 Predicate only_if_olc_nonzero = Predicate.Default;
473 for(int olc : new int[] { 1, 0 }) {
474 for(boolean predicate_olc_nonzero : new boolean[] { true, false }) {
475 prln("Attempting send token with "+
477 "predicate olc"+(predicate_olc_nonzero?"!=0":"==0"));
479 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, 1));
481 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC, SetDest.OuterLoopCounter, SetSource.Decrement));
482 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, 1));
483 marina.instrIn.fill(new Instruction.Move(DOCK,
484 false, /* requeueing */
485 predicate_olc_nonzero /* predicate */
486 ? only_if_olc_nonzero
489 false, /* torpedoable */
493 false, /* latchData */
494 false, /* latchPath */
498 toks = marina.tokOut.drainMany();
499 int expected = (predicate_olc_nonzero == (olc!=0)) ? 1 : 0;
500 fatal(toks.size()!=expected, "Expected "+expected+" token to emerge but got: "+toks.size()+" token(s)");
505 prln("End testFlagZ");
508 private void testPredicationOnAB(Marina marina) {
509 prln("Begin testPredicationOnAB");
512 List<BitVector> toks;
514 prln("Setting OLC=63");
515 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, 63));
517 for(boolean flag_a : new boolean[] { false, true }) {
518 for(boolean flag_b : new boolean[] { false, true }) {
519 prln("Setting flags, a="+flag_a+" b="+flag_b);
520 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,
522 ? Instruction.Set.FlagFunction.ONE
523 : Instruction.Set.FlagFunction.ZERO,
525 ? Instruction.Set.FlagFunction.ONE
526 : Instruction.Set.FlagFunction.ZERO
528 getCtrsFlags(marina);
531 for(Predicate predicate : new Predicate[] {
539 prln("Attempting send token with a="+flag_a+", b="+flag_b+", predicate="+predicate.getClass().getName());
541 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, 1));
542 marina.instrIn.fill(new Instruction.Move(DOCK,
543 false, /* requeueing */
544 predicate, /* predicate */
545 false, /* torpedoable */
549 false, /* latchData */
550 false, /* latchPath */
555 toks = marina.tokOut.drainMany();
556 int expected = predicate.evaluate(flag_a, flag_b, false, false) ? 1 : 0;
557 fatal(toks.size()!=expected, "Expected "+expected+" token to emerge but got: "+
558 toks.size()+" token(s)");
564 prln("End testPredicationOnAB");
567 private void getCtrsFlags(Marina marina) {
568 prln("begin getCtrsFlags");
571 int olc = marina.getOLC();
574 Ilc ilc = marina.getILC();
575 prln("ILC.done=="+ilc.getDone()+
576 " ILC.infinity=="+ilc.getInfinity()+
577 " ILC.zero=="+ilc.getZero()+
578 " ILC.count=="+ilc.getCount());
580 boolean a = marina.getFlagA();
583 boolean b = marina.getFlagB();
586 boolean c = marina.getFlagC();
590 prln("end getCtrsFlags");
592 private void walkOneOLC(Marina marina) {
593 prln("Begin walkOneOLC");
595 for (int i=0; i<7; i++) {
596 int inOlc = 0x20 >> i;
597 prln("inOlc="+inOlc);
598 marina.instrIn.fill(new
599 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, inOlc));
600 int outOlc = marina.getOLC();
601 fatal(outOlc!=inOlc, "walkOneOLC: got="+outOlc+" expected="+inOlc);
604 prln("End walkOneOLC");
606 private void walkOneILC(Marina marina) {
607 prln("Begin walkOneILC");
609 for (int i=0; i<7; i++) {
610 // Mask off the "zero" bit position
611 int inIlc = 0x20 >> i;
612 prln("inIlc="+inIlc);
614 marina.instrIn.fill(new
615 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, inIlc));
617 Ilc ilc = marina.getILC();
618 int outIlc = ilc.getCount();
619 fatal(outIlc!=inIlc, "bad ILC count: "+outIlc+" expected: "+outIlc);
621 boolean inZero = inIlc==0;
622 boolean outZero = ilc.getZero();
623 fatal(outZero!=inZero, "bad ILC zero: "+outZero);
626 prln("End walkOneILC");
628 private void countIlc(Marina marina) {
629 final int maxIlc = 63;
630 prln("Begin countIlc");
633 marina.instrIn.fill(new
634 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, maxIlc));
636 int ilc = marina.getILC().getCount();
637 fatal(ilc!=maxIlc, "bad ILC count: "+ilc+" expected: "+maxIlc);
639 // execute a move instruction that does nothing except decrement the ILC to zero
641 new Instruction.Move(DOCK,
642 false, /* requeueing */
643 Predicate.IgnoreOLC, /* predicate */
644 false, /* torpedoable */
648 false, /* latchData */
649 false, /* latchPath */
654 // wait for ILC to count from 63 to 0
655 model.waitNS(64 * CYCLE_TIME_NS);
657 ilc = marina.getILC().getCount();
658 fatal(ilc!=0, "bad ILC count: "+ilc+" expected: "+0);
661 prln("End countIlc");
663 // Note: countOlc takes 44 minutes to run on nanosim
664 private void countOlc(Marina marina) {
665 final int maxOlc = 63;
666 prln("Begin countOlc");
669 marina.instrIn.fill(new
670 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, maxOlc));
671 for (int i=maxOlc; i>=0; i--) {
672 prln("OLC should be: "+i);
673 int olc = marina.getOLC();
674 fatal(olc!=i, "bad OLC: "+olc+" expected: "+i);
675 marina.instrIn.fill(new
676 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, SetSource.Decrement));
680 prln("End countOlc");
683 private void saturateInstructionFifo(Marina marina, Instruction instruction, int quantity, boolean expect_it_to_jam_up) {
684 prln("Inserting "+quantity+" copies of \"" + instruction + "\"");
687 for(i=0; i<quantity; i++) {
688 prln("Inserting instruction " + (i+1) +"/"+ quantity);
689 marina.instrIn.fill(instruction);
690 boolean jammed = (marina.instrIn.getFillStateWire()==MarinaUtils.StateWireState.FULL);
691 if (jammed && expect_it_to_jam_up) {
692 prln("Stopper remained full after inserting instruction; this was expected; we are happy.");
696 fatal(jammed, "Instruction stopper did not drain after inserting " + (i+1) + " instructions; not good!");
698 fatal(expect_it_to_jam_up, "Expected instruction stopper to jam up, but it did not");
700 prln("Successfully inserted " + i + " instructions");
703 private static final Instruction NOP =
704 new Instruction.Move(DOCK,
705 false, /* requeueing */
706 Predicate.IgnoreOLC, /* predicate */
707 false, /* torpedoable */
711 false, /* latchData */
712 false, /* latchPath */
717 private static final Instruction REQUEUEING_NOP =
718 new Instruction.Move(DOCK,
719 true, /* requeueing */
720 Predicate.IgnoreOLC, /* predicate */
721 false, /* torpedoable */
725 false, /* latchData */
726 false, /* latchPath */
731 private static final Instruction SEND_DATA =
732 new Instruction.Move(DOCK,
733 false, /* requeueing */
734 Predicate.IgnoreOLC, /* predicate */
735 false, /* torpedoable */
739 false, /* latchData */
740 false, /* latchPath */
745 private static final Instruction REQUEUEING_SEND_DATA =
746 new Instruction.Move(DOCK,
747 true, /* requeueing */
748 Predicate.IgnoreOLC, /* predicate */
749 false, /* torpedoable */
753 false, /* latchData */
754 false, /* latchPath */
759 private void testRequeueStage0(Marina marina) {
760 prln("Begin testRequeueStage0");
763 prln("Executing Set OLC=1");
764 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,1));
765 prln("Executing Set OLC--");
766 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,SetSource.Decrement));
767 saturateInstructionFifo(marina, REQUEUEING_NOP, MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT, false);
769 prln("End testRequeueStage0");
772 private void testRequeueStage0to1(Marina marina) {
773 prln("Begin testRequeueStage0to1");
776 prln("Executing Set OLC=63");
777 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,63));
778 saturateInstructionFifo(marina, REQUEUEING_NOP, MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT, true);
780 prln("End testRequeueStage0to1");
784 * This test brings the requeue stage through the 0->1->3 state
785 * transition sequence.
788 * According to the diagram in IES50, there are two transitions
789 * (0->1, 1->3) to perform, and in each state there are two
790 * behaviors to verify (the two notations in each oval of the
791 * state diagram). The "OD->drain" behavior of state 0 is
792 * verified by testRequeueStage0().
794 private void testRequeueStage0to1to3to0(Marina marina) {
795 List<BitVector> dataItems;
799 prln("Begin testRequeueStage0to1to3to0");
802 // State 0 //////////////////////////////////////////////////////////////////////////////
804 prln("Executing Set OLC="+olc_value);
805 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,olc_value));
806 prln("Executing Set ILC=1");
807 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, 1));
809 // verify state0 "EPI->ring" and 0->1 transition
810 prln("Executing Send Data (requeueable); this will cause 0->1 transition and be discarded");
811 marina.instrIn.fill(REQUEUEING_SEND_DATA);
813 // State 1 //////////////////////////////////////////////////////////////////////////////
815 // verify state1 "EPI->ring"
816 prln("Executing Set ILC=1; this will be recirculated");
817 marina.instrIn.fill(new Instruction.Set(DOCK,true,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, 1));
819 prln("Executing Send Data; this will be recirculated");
820 marina.instrIn.fill(REQUEUEING_SEND_DATA);
822 prln("Executing Set OLC--; this will be recirculated");
823 marina.instrIn.fill(new Instruction.Set(DOCK,true,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,SetSource.Decrement));
825 // verify state1 "OD waits"
826 dataItems = marina.data.drainMany(2);
827 fatal(dataItems.size()!=1, "Expected exactly one data item to emerge but got: "+dataItems.size()+" data items");
829 // verify 1->3 transition
830 prln("Executing Tail; this will cause the 2->3 transition and be discarded");
831 marina.instrIn.fill(new Instruction.Tail(DOCK));
833 // State 3 //////////////////////////////////////////////////////////////////////////////
835 // verify state3 "OD->ring"
836 dataItems = marina.data.drainMany(MORE_THAN_DATA_OUT_SATURATION_AMOUNT);
837 fatal(dataItems.size()<MORE_THAN_DATA_OUT_SATURATION_AMOUNT,
838 "Expected an endless supply of data items, but only got: "+dataItems.size()+" of them");
840 // verify state3 "OD->ring"
841 saturateInstructionFifo(marina, NOP, MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT, true);
843 // verify state3->state0
844 dataItems = marina.data.drainMany(olc_value);
845 fatal(dataItems.size()>=olc_value,
846 "Expected less than " + olc_value + " items to emerge, but got at least : "+dataItems.size()+" of them");
848 // State 0 //////////////////////////////////////////////////////////////////////////////
850 // verify that we are back in state0
851 saturateInstructionFifo(marina, REQUEUEING_NOP, MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT, false);
854 prln("End testRequeueStage0to1to3to0");
857 private void testWaitForTail(Marina marina) {
858 List<BitVector> dataItems;
860 prln("Begin testWaitForTail");
863 prln("inserting instruction: Set OLC=63");
864 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,63));
866 prln("inserting instruction: [Rq] Nop; this will cause 0->1 transition and possibly be discarded");
867 marina.instrIn.fill(REQUEUEING_NOP);
869 // just in case there is some capacity between the execution
870 // stage and the requeue stage, we stick in a whole bunch of
872 for(int i=0; i<4; i++) {
873 prln("inserting instruction: [Rq] Nop; this (and subsequent instructions) should not execute until Tail is inserted");
874 marina.instrIn.fill(REQUEUEING_NOP);
877 prln("inserting instruction: [Rq] Set ILC=1");
878 marina.instrIn.fill(new Instruction.Set(DOCK,true,Predicate.IgnoreOLC,SetDest.InnerLoopCounter,1));
880 prln("inserting instruction: [Rq] Send Data");
881 marina.instrIn.fill(REQUEUEING_SEND_DATA);
883 dataItems = marina.data.drainMany(1);
884 fatal(dataItems.size()!=0, "Expected exactly no data items to emerge but got at least: "+dataItems.size());
887 prln("End testWaitForTail");
890 private void testRequeueStageDrop(Marina marina) {
891 List<BitVector> dataItems;
893 prln("Begin testRequeueStageDrop");
896 prln("inserting instruction: Set OLC=63");
897 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,63));
899 prln("inserting instruction: Set ILC=1");
900 marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter,1));
902 // if you uncomment this, then the NOP will be dropped and the test will pass
904 prln("inserting instruction: [Rq] Nop; this will cause 0->1 transition and possibly be discarded");
905 marina.instrIn.fill(REQUEUEING_NOP);
908 prln("inserting instruction: [Rq] Send Data; this will cause 0->1 transition and be discarded");
909 marina.instrIn.fill(REQUEUEING_SEND_DATA);
911 prln("inserting instruction: [Rq] Set ILC=1");
912 marina.instrIn.fill(new Instruction.Set(DOCK,true,Predicate.IgnoreOLC,SetDest.InnerLoopCounter,1));
914 prln("inserting instruction: Tail");
915 marina.instrIn.fill(new Instruction.Tail(DOCK));
917 dataItems = marina.data.drainMany(3);
918 fatal(dataItems.size()<3, "Expected exactly unlimited data items to emerge but got only: "+dataItems.size());
921 prln("End testRequeueStageDrop");
925 private void testFlagAB(Marina marina) {
926 prln("Begin testFlagAB");
929 Instruction.Set.FlagFunction zero = Instruction.Set.FlagFunction.ZERO;
930 Instruction.Set.FlagFunction one = zero;
933 // we should be able to use any pair of FlagX+NotFlagX,
934 // but we toss them all in to maximize the chances of the
935 // test passing (later we will try the individual
936 // combinations to maximize the chances of failure).
937 one = one.add(Predicate.FlagA);
938 one = one.add(Predicate.NotFlagA);
939 one = one.add(Predicate.FlagB);
940 one = one.add(Predicate.NotFlagB);
941 one = one.add(Predicate.FlagC);
942 one = one.add(Predicate.NotFlagC);
944 // clear the flags to a known state, then check both 0->1 and 1->0 transitions
945 for(boolean b : new boolean[] { false, true, false }) {
946 prln((b?"Setting":"Clearing")+" flags");
948 marina.instrIn.fill(new
949 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,
953 fatal(marina.getFlagA()!=b, "after "+(b?"setting":"clearing")+" FlagA, it was still "+(b?"clear":"set"));
954 fatal(marina.getFlagB()!=b, "after "+(b?"setting":"clearing")+" FlagB, it was still "+(b?"clear":"set"));
958 prln("End testFlagAB");
960 private void sendTorpedo(Marina marina) {
961 prln("Begin sendTorpedo");
965 marina.instrIn.fill(new
966 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, 63));
968 int olc = marina.getOLC();
969 fatal(olc!=63, "bad OLC: "+olc+" expected: 63");
972 marina.instrIn.fill(new
973 Instruction.Set(DOCK,false,Predicate.IgnoreOLC, CLEAR_FLAG, CLEAR_FLAG));
975 fatal(marina.getFlagA(), "bad A flag: true");
976 fatal(marina.getFlagB(), "bad B flag: true");
978 prln("ILC = Infinity");
979 marina.instrIn.fill(new
980 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, SetSource.Infinity));
982 prln("execute a move instruction that does nothing but loops until torpedo arrives");
984 new Instruction.Move(DOCK,
985 false, /* requeueing */
986 Predicate.IgnoreOLC, /* predicate */
987 true, /* torpedoable */
991 false, /* latchData */
992 false, /* latchPath */
997 prln("NOP This instruction can't predicate on OLC because of a hardware bug");
998 marina.instrIn.fill(new
999 Instruction.Set(DOCK,false,Predicate.Default, A_FLAG, B_FLAG));
1001 prln("A=1, B=1 This instruction should get torpedoed along with the Move");
1002 marina.instrIn.fill(new
1003 Instruction.Set(DOCK,false,Predicate.Default, SET_FLAG, SET_FLAG));
1005 prln("send torpedo. This should clear the OLC");
1006 marina.instrIn.fill(InstructionStopper.TORPEDO);
1008 getCtrsFlags(marina);
1010 prln("A and B should remain false");
1011 fatal(marina.getFlagA(), "bad A flag: true");
1012 fatal(marina.getFlagB(), "bad B flag: true");
1014 prln("OLC = 63. Reload OLC after torpedo");
1015 marina.instrIn.fill(new
1016 Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, 63));
1018 olc = marina.getOLC();
1019 fatal(olc!=63, "bad OLC: "+olc+" expected: 63");
1021 prln("A=1, B=1 This instruction should execute because OLC!=0");
1022 marina.instrIn.fill(new
1023 Instruction.Set(DOCK,false,Predicate.Default, SET_FLAG, SET_FLAG));
1025 prln("A and B should be true");
1026 fatal(!marina.getFlagA(), "bad A flag: false");
1027 fatal(!marina.getFlagB(), "bad B flag: false");
1030 prln("End sendTorpedo");
1032 private void doOneTest(int testNum) {
1033 prln("MarinaTest: performing test: "+testNum);
1034 marina.masterClear(tester);
1036 marina.enableInstructionSend(true);
1039 case 2: sendInstructions(marina); break;
1040 case 3: sendToken(marina); break;
1041 case 4: getCtrsFlags(marina); break;
1042 case 5: walkOneOLC(marina); break;
1044 // Russell's tests begin with 1000
1045 case 1000: walkOneILC(marina); break;
1046 case 1001: countIlc(marina); break;
1047 case 1002: countOlc(marina); break;
1048 case 1003: sendTorpedo(marina); break;
1050 // Bill's tests begin with 2000
1053 // Adam's tests begin with 3000
1054 case 3000: sendToken(marina); break;
1055 case 3001: testFlagAB(marina); break;
1056 case 3002: testRequeueStage0(marina); break;
1057 case 3003: testRequeueStage0to1(marina); break;
1058 case 3004: testFlagZ(marina); break;
1059 case 3005: testPredicationOnAB(marina); break;
1060 case 3006: sendData(marina); break;
1061 case 3007: testRequeueStage0to1to3to0(marina); break;
1062 case 3008: testWaitForTail(marina); break;
1063 case 3009: testRequeueStageDrop(marina); break;
1066 fatal(true, "Test number: "+testNum+" doesn't exist.");
1069 // If we get here then test passed
1074 //============================ for public use =============================
1077 public static void main(String[] args) {
1078 startTime = System.currentTimeMillis();
1079 new MarinaTest(args);