add test 3010, testRequeueStage0to2to3to0
authorAdam Megacz <adam.megacz@sun.com>
Thu, 20 Nov 2008 23:22:41 +0000 (23:22 +0000)
committerAdam Megacz <adam.megacz@sun.com>
Thu, 20 Nov 2008 23:22:41 +0000 (23:22 +0000)
testCode/com/sun/vlsi/chips/marina/test/MarinaTest.java

index 153856b..0724846 100644 (file)
@@ -69,6 +69,10 @@ public class MarinaTest {
     // will never cause them to operate incorrectly.
     private static final int MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT = 25;
        
+    // This is the number of items which can be in the instruction
+    // fifo ring WITHOUT causing it to stop circulating.
+    private static final int INSTRUCTION_RING_CAPACITY = 13;
+       
     // Officially, this should be the number of data items which can
     // be sent from the dock while the "data" proper stopper is in
     // the "stopped" state
@@ -81,10 +85,10 @@ public class MarinaTest {
     private static final int DATA_OUT_SATURATION_AMOUNT = XXX;
     */
 
-    // This is some number which is significantly greater than
-    // DATA_OUT_SATURATION_AMOUNT.  Increasing it may slow the tests down, but
-    // will never cause them to operate incorrectly.
-    private static final int MORE_THAN_DATA_OUT_SATURATION_AMOUNT = 16;
+    // This is some number which is greater than
+    // DATA_OUT_SATURATION_AMOUNT, but less than the capacity of the
+    // instruction fifo.
+    private static final int MORE_THAN_DATA_OUT_SATURATION_AMOUNT = 10;
        
        // Nominal cycle time assuming 4 GHz throughput
        private static final double CYCLE_TIME_NS = 0.250;
@@ -457,6 +461,13 @@ public class MarinaTest {
        prln("End sendData");
     }
 
+    private void setOLC(Marina marina, int olc) {
+        // ugly hack, to be removed when we fix the zero-detect circuit
+        for(int i=0; i<2; i++) {
+            marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, olc));
+        }
+    }
+
     private void testFlagZ(Marina marina) {
        prln("Begin testFlagZ");
        adjustIndent(2);
@@ -474,7 +485,7 @@ public class MarinaTest {
                 adjustIndent(2);
 
                 prln("Inserting Set OLC="+olc);
-                marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, olc));
+                setOLC(marina, olc);
 
                 prln("Inserting ["+(predicate_olc_nonzero?"olc!=0":"olc==0")+"] send data");
                 marina.instrIn.fill(new Instruction.Move(DOCK,
@@ -509,7 +520,7 @@ public class MarinaTest {
         List<BitVector> toks;
 
         prln("Setting OLC=63");
-        marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter, 63));
+        setOLC(marina, 63);
 
         for(boolean flag_a : new boolean[] { false, true }) {
             for(boolean flag_b : new boolean[] { false, true }) {
@@ -764,7 +775,7 @@ public class MarinaTest {
        adjustIndent(2);
 
         prln("Executing Set OLC=0");
-        marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,0));
+        setOLC(marina, 0);
         saturateInstructionFifo(marina, REQUEUEING_NOP, MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT, false);
        adjustIndent(-2);
         prln("End testRequeueStage0");
@@ -775,19 +786,19 @@ public class MarinaTest {
        adjustIndent(2);
 
         prln("Executing Set OLC=63");
-        marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,63));
+        setOLC(marina, 63);
         saturateInstructionFifo(marina, REQUEUEING_NOP, MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT, true);
        adjustIndent(-2);
         prln("End testRequeueStage0to1");
     }
 
     /**
-     *  This test brings the requeue stage through the 0->1->3 state
+     *  This test brings the requeue stage through the 0->1->3->0 state
      *  transition sequence.
      *
 
-     *  According to the diagram in IES50, there are two transitions
-     *  (0->1, 1->3) to perform, and in each state there are two
+     *  According to the diagram in IES50, there are three transitions
+     *  (0->1, 1->3, 3->0) to perform, and in each state there are two
      *  behaviors to verify (the two notations in each oval of the
      *  state diagram).  The "OD->drain" behavior of state 0 is
      *  verified by testRequeueStage0().
@@ -803,7 +814,7 @@ public class MarinaTest {
         // State 0 //////////////////////////////////////////////////////////////////////////////
 
         prln("Executing Set OLC="+olc_value);
-        marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,olc_value));
+        setOLC(marina, olc_value);
        prln("Executing Set ILC=1");
        marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, 1));
 
@@ -855,6 +866,95 @@ public class MarinaTest {
         prln("End testRequeueStage0to1to3to0");
     }
 
+    /**
+     *  This test brings the requeue stage through the 0->2->3->0 state
+     *  transition sequence.
+     *
+
+     *  According to the diagram in IES50, there are two transitions
+     *  (0->2, 2->3, 3->0) to perform, and in each state there are two
+     *  behaviors to verify (the two notations in each oval of the
+     *  state diagram).  The "OD->drain" behavior of state 0 is
+     *  verified by testRequeueStage0().
+     */
+    private void testRequeueStage0to2to3to0(Marina marina) {
+        List<BitVector> dataItems;
+
+        int olc_value = 10;
+        int number_of_non_requeueable_send_datas = INSTRUCTION_RING_CAPACITY;
+
+        prln("Begin testRequeueStage0to2to3to0");
+       adjustIndent(2);
+
+        // State 0 //////////////////////////////////////////////////////////////////////////////
+
+        prln("Executing Set OLC="+olc_value);
+        setOLC(marina, olc_value);
+
+       prln("Executing Set ILC=1");
+       marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter, 1));
+
+        // insert many non-requeueing "send data item" instructions;
+        // this will let us single-step the execution point by
+        // extracting data items.
+        for(int i=0; i<number_of_non_requeueable_send_datas; i++) {
+            prln("Inserting Send Data");
+            marina.instrIn.fill(SEND_DATA);
+        }
+
+        // this will send us a token later
+       prln("Inserting [Rq] Nop; this will be discarded");
+        marina.instrIn.fill(REQUEUEING_NOP);
+
+        // this will send us a token later
+       prln("Inserting [Rq] Send Data; this will be recirculated");
+        marina.instrIn.fill(REQUEUEING_SEND_DATA);
+
+       prln("Inserting [Rq] Set OLC--; this will be recirculated");
+        marina.instrIn.fill(new Instruction.Set(DOCK,true,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,SetSource.Decrement));
+
+        // insert the tail, which will cause the 0->2 transition
+       prln("Inserting Tail");
+       marina.instrIn.fill(new Instruction.Tail(DOCK));
+
+        // State 2 //////////////////////////////////////////////////////////////////////////////
+
+        // confirm state 2 "EPI waits"
+       prln("Saturating the instruction input to confirm that EPI waits");
+        saturateInstructionFifo(marina, REQUEUEING_NOP, MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT, true);
+
+        // confirm state 2 "OD->drain"
+       prln("Draining data output to cause the 2->3 transition");
+        dataItems = marina.data.drainMany(number_of_non_requeueable_send_datas);
+        fatal(dataItems.size()!=number_of_non_requeueable_send_datas,
+              "Expected at least " + number_of_non_requeueable_send_datas +
+              " items to emerge, but got only : "+dataItems.size()+" of them");
+
+        // State 3 //////////////////////////////////////////////////////////////////////////////
+
+        // verify state3 "EPI waits"
+       prln("Verifying that EPI still waits in state3");
+        fatal(marina.instrIn.getFillStateWire()!=MarinaUtils.StateWireState.FULL,
+              "state3 EPI waits not verified");
+       prln("  ok");
+       prln("");
+
+        // verify state3 "OD->ring" and state3->state0
+       prln("Removing data items to run down the OLC to zero and cause 3->0 transition");
+        dataItems = marina.data.drainMany(olc_value+10);
+        fatal(dataItems.size()!=(olc_value+1),
+              "Expected exactly " + (olc_value+1) + " items to emerge, but got: "+dataItems.size()+" of them");
+
+        // State 0 //////////////////////////////////////////////////////////////////////////////
+
+        // verify that we are back in state0
+       prln("Confirming that we are back in state0");
+        saturateInstructionFifo(marina, REQUEUEING_NOP, MORE_THAN_INSTRUCTION_IN_SATURATION_AMOUNT, false);
+
+       adjustIndent(-2);
+        prln("End testRequeueStage0to2to3to0");
+    }
+
     private void testWaitForTail(Marina marina) {
         List<BitVector> dataItems;
 
@@ -862,7 +962,7 @@ public class MarinaTest {
        adjustIndent(2);
 
         prln("inserting instruction: Set OLC=63");
-        marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,63));
+        setOLC(marina, 63);
 
        prln("inserting instruction: [Rq] Nop; this will cause 0->1 transition and possibly be discarded");
         marina.instrIn.fill(REQUEUEING_NOP);
@@ -888,6 +988,10 @@ public class MarinaTest {
         prln("End testWaitForTail");
     }
 
+    // This test case will FAIL if the requeue stage behaves as
+    // described in IES50.  If we determine that the behavior
+    // described there is actually desirable, then this test should be
+    // modified.
     private void testRequeueStageDrop(Marina marina) {
         List<BitVector> dataItems;
 
@@ -895,7 +999,7 @@ public class MarinaTest {
        adjustIndent(2);
 
         prln("inserting instruction: Set OLC=63");
-        marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.OuterLoopCounter,63));
+        setOLC(marina, 63);
 
        prln("inserting instruction: Set ILC=1");
        marina.instrIn.fill(new Instruction.Set(DOCK,false,Predicate.IgnoreOLC,SetDest.InnerLoopCounter,1));
@@ -1061,6 +1165,7 @@ public class MarinaTest {
                case 3007: testRequeueStage0to1to3to0(marina); break;
                case 3008: testWaitForTail(marina); break;
                case 3009: testRequeueStageDrop(marina); break;         
+               case 3010: testRequeueStage0to2to3to0(marina); break;
 
                default:
                        fatal(true, "Test number: "+testNum+" doesn't exist.");