Esempio n. 1
0
        protected bool rb_inject(Flit[] input)
        {
            bool redirection = false;
            Flit temp        = null;

            if (rbuf.isEmpty())
            {
                rb_inject_block_count = 0;
            }

            if (rb_inject_block_count > Config.redirectThreshold)
            {
                redirection = true;
            }

            if (redirection)
            {
                int rand = Simulator.rand.Next(TOTAL_DIR);

                if (input[rand] != null && !Simulator.network.golden.isGolden(input[rand]))
                {
                    temp                  = input[rand];
                    input[rand]           = null;
                    rb_inject_block_count = 0;
                }
            }

            int injectedCount = 0;

            // Resubmit Buffer Injection
            for (int i = 0; i < TOTAL_DIR; i++)
            {
                if (rbuf.isEmpty() || injectedCount == Config.rbInjectCount)
                {
                    break;
                }

                if (input[i] == null)
                {
                    input[i] = rbuf.removeFlit();
                    injectedCount++;
                    Simulator.stats.rb_injectCount.Add();
                }
            }

            if (!rbuf.isEmpty() && injectedCount == 0)
            {
                rb_inject_block_count++;
            }

            if (redirection && temp != null)
            {
                Simulator.stats.redirectedFlits.Add();
                Simulator.stats.rb_ejectCount.Add();
                rbuf.addFlit(temp);
            }
            return(redirection);
        }
Esempio n. 2
0
        Flit[] input = new Flit[4]; // keep this as a member var so we don't
        // have to allocate on every step (why can't
        // we have arrays on the stack like in C?)

        protected override void _doStep()
        {
            Flit[] eject = new Flit[4];
            eject[0] = eject[1] = eject[2] = eject[3] = null;

            int wantToEject = 0;

            for (int i = 0; i < 4; i++)
            {
                if (linkIn[i] != null && linkIn[i].Out != null)
                {
                    if (linkIn[i].Out.dest.x == coord.x && linkIn[i].Out.dest.y == coord.y)
                    {
                        wantToEject++;
                    }
                }
            }

            switch (wantToEject)
            {
            case 0: Simulator.stats.eject_0.Add(); break;

            case 1: Simulator.stats.eject_1.Add(); break;

            case 2: Simulator.stats.eject_2.Add(); break;

            case 3: Simulator.stats.eject_3.Add(); break;

            case 4: Simulator.stats.eject_4.Add(); break;

            default: throw new Exception("Eject problem");
            }

            for (int i = 0; i < Config.ejectCount; i++)
            {
                eject[i] = ejectLocal();
            }

            for (int i = 0; i < 4; i++)
            {
                input[i] = null;
            }

            // grab inputs into a local array so we can sort
            int c = 0;

            for (int dir = 0; dir < 4; dir++)
            {
                if (linkIn[dir] != null && linkIn[dir].Out != null)
                {
                    input[c++]            = linkIn[dir].Out;
                    linkIn[dir].Out.inDir = dir;
                    linkIn[dir].Out       = null;
                }
            }

            int before = 0;

            for (int i = 0; i < 4; i++)
            {
                if (input[i] != null)
                {
                    before++;
                }
            }

            int reinjectedCount = 0;

            if (Config.resubmitBuffer)
            {
                if (!rBuf.isEmpty())
                {
                    for (int i = 0; i < 4; i++)
                    {
                        if (reinjectedCount < Config.rebufInjectCount)
                        {
                            if (input[i] == null && !rBuf.isEmpty())
                            {
                                input[i] = rBuf.removeFlit();
                                input[i].nrInRebuf++;
                                reinjectedCount++;
                            }
                        }
                    }
                }
            }

            int after = 0;

            for (int i = 0; i < 4; i++)
            {
                if (input[i] != null)
                {
                    after++;
                }
            }
            if (before + reinjectedCount != after)
            {
                throw new Exception("Something weird happened on resubmit buffer");
            }

            /*for (int i = 0; i < 4; i++)
             *  for (int j = 0; j < 4; j++)
             *  {
             *      if (input[i] == null || input[j] == null)
             *          continue;
             *      if (i != j && input[i].Equals(input[j]))
             *          throw new Exception("DUPLICATING");
             *  }
             */
            // sometimes network-meddling such as flit-injection can put unexpected
            // things in outlinks...
            int outCount = 0;

            for (int dir = 0; dir < 4; dir++)
            {
                if (linkOut[dir] != null && linkOut[dir].In != null)
                {
                    outCount++;
                }
            }

            bool wantToInject = m_injectSlot2 != null || m_injectSlot != null;
            bool canInject    = (c + outCount) < neighbors;
            bool starved      = wantToInject && !canInject;

            if (starved)
            {
                Flit starvedFlit = null;
                if (starvedFlit == null)
                {
                    starvedFlit = m_injectSlot2;
                }
                if (starvedFlit == null)
                {
                    starvedFlit = m_injectSlot;
                }

                Simulator.controller.reportStarve(coord.ID);
                statsStarve(starvedFlit);
            }
            if (canInject && wantToInject)
            {
                Flit inj_peek = null;
                if (m_injectSlot2 != null)
                {
                    inj_peek = m_injectSlot2;
                }
                else if (m_injectSlot != null)
                {
                    inj_peek = m_injectSlot;
                }
                if (inj_peek == null)
                {
                    throw new Exception("Inj flit peek is null!!");
                }

                if (!Simulator.controller.ThrottleAtRouter || Simulator.controller.tryInject(coord.ID))
                {
                    Flit inj = null;
                    if (m_injectSlot2 != null)
                    {
                        inj           = m_injectSlot2;
                        m_injectSlot2 = null;
                    }
                    else if (m_injectSlot != null)
                    {
                        inj          = m_injectSlot;
                        m_injectSlot = null;
                    }
                    else
                    {
                        throw new Exception("what???inject null flits??");
                    }
                    input[c++] = inj;
#if DEBUG
                    Console.WriteLine("injecting flit {0}.{1} at node {2} cyc {3}",
                                      m_injectSlot.packet.ID, m_injectSlot.flitNr, coord, Simulator.CurrentRound);
#endif
#if memD
                    int r = inj.packet.requesterID;
                    if (r == coord.ID)
                    {
                        Console.WriteLine("inject flit at node {0}<>request:{1}", coord.ID, r);
                    }
                    else
                    {
                        Console.WriteLine("Diff***inject flit at node {0}<>request:{1}", coord.ID, r);
                    }
#endif
                    statsInjectFlit(inj);
                }
            }

            for (int i = 0; i < Config.ejectCount; i++)
            {
                if (eject[i] != null)
                {
                    acceptFlit(eject[i]);
                }
            }

            // inline bubble sort is faster for this size than Array.Sort()
            // sort input[] by descending priority. rank(a,b) < 0 iff a has higher priority.
            for (int i = 0; i < 4; i++)
            {
                for (int j = i + 1; j < 4; j++)
                {
                    if (input[j] != null &&
                        (input[i] == null ||
                         rank(input[j], input[i]) < 0))
                    {
                        Flit t = input[i];
                        input[i] = input[j];
                        input[j] = t;
                    }
                }
            }

            //int resubmittedCount = 0;
            //int numDeflected = 0;
            int[] deflected = new int[4];
            deflected[0] = deflected[1] = deflected[2] = deflected[3] = -1;

            // assign outputs
            for (int i = 0; i < 4 && input[i] != null; i++)
            {
                PreferredDirection pd = determineDirection(input[i], coord);
                int  outDir           = -1;
                Flit tempFlit         = input[i];



                if (pd.xDir != Simulator.DIR_NONE && linkOut[pd.xDir].In == null)
                {
                    linkOut[pd.xDir].In = input[i];
                    outDir = pd.xDir;

                    /* Refresh wasInBuf */
                    if (Config.wasInRebufCycleRefresh)
                    {
                        tempFlit.wasInRebuf = false;
                    }
                }

                else if (pd.yDir != Simulator.DIR_NONE && linkOut[pd.yDir].In == null)
                {
                    linkOut[pd.yDir].In = input[i];
                    outDir = pd.yDir;

                    /* Refresh wasInBuf */
                    if (Config.wasInRebufCycleRefresh)
                    {
                        tempFlit.wasInRebuf = false;
                    }
                }

                // deflect!
                else
                {
                    input[i].Deflected = true;
                    int dir = 0;

                    /*deflected[numDeflected] = i;
                     * numDeflected++;
                     *
                     */

                    if (Config.randomize_defl)
                    {
                        dir = Simulator.rand.Next(4); // randomize deflection dir (so no bias)
                    }
                    for (int count = 0; count < 4; count++, dir = (dir + 1) % 4)
                    {
                        if (linkOut[dir] != null && linkOut[dir].In == null)
                        {
                            linkOut[dir].In = input[i];
                            outDir          = dir;
                            break;
                        }
                    }

                    if (outDir == -1)
                    {
                        throw new Exception(
                                  String.Format("Ran out of outlinks in arbitration at node {0} on input {1} cycle {2} flit {3} c {4} neighbors {5} outcount {6}", coord, i, Simulator.CurrentRound, input[i], c, neighbors, outCount));
                    }
                }
            }

            /*
             * if (Config.resubmitBuffer)
             *  sortDeflected(deflected);
             *
             * for (int i = 0; i < 4; i++)
             * {
             *  if (deflected[i] == -1)
             *      break;
             *  else
             *  {
             *      int dir = 0;
             *      if (Config.randomize_defl)
             *          dir = Simulator.rand.Next(4);
             *
             *      for (int count = 0; count < 4; count++, dir = (dir + 1) % 4) {
             *          if(linkOut[dir] != null && linkOut[dir].In == null) {
             *              linkOut[dir].In = input[deflected[i]];
             *              //outDir = dir;
             *              break;
             *          }
             *      }
             *  }
             * }
             */
        }
Esempio n. 3
0
        Flit[] input = new Flit[6]; // keep this as a member var so we don't
                                    // have to allocate on every step (why can't
                                    // we have arrays on the stack like in C?)
                                    // --- because we have a garbage collector instead and want to dynamically allocate everything

        protected override void _doStep()
        {
            int tempCount = 0;

            /* Setup the inputs */
            for (int dir = 0; dir < 6; dir++)
            {
                if (linkIn[dir] != null && linkIn[dir].Out != null)
                {
                    tempCount++;
                    input[dir]       = linkIn[dir].Out;
                    input[dir].inDir = dir;
                }
                else
                {
                    input[dir] = null;
                }
            }

            //To avoid the create / remove counter exception
            if (injectPlaceholder > 0)
            {
                tempCount++;
            }

            /* Only used when forcing a placeholder into the system */
            int tempDir = (clockwise) ? Simulator.DIR_CCW : Simulator.DIR_CW;

            if (input[tempDir] == null && !rBuf.isEmpty())
            {
                input[tempDir] = rBuf.removeFlit();
            }
            else if (input[connectionDirection] == null && !rBuf.isEmpty())
            {
                input[connectionDirection] = rBuf.removeFlit();
            }

            route();

            int endCount = 0;

            /* Assign outputs */
            for (int dir = 0; dir < 6; dir++)
            {
                if (input[dir] != null)
                {
#if FLIT
                    Console.WriteLine("flit {0}.{1} at node {2} cyc {3} \t | dir:{4} | dest: {5} connectionDir {6} productive: {7} isDest {8}", input[dir].packet.ID, input[dir].flitNr, ringCoord, Simulator.CurrentRound, dir, input[dir].packet.ringdest, connectionDirection, isRingProductive(input[dir], connectionDirection), isDestRing(input[dir]));
                    Console.WriteLine("\tflit {0}.{1} currentRing = {2} destRing = {3},{4}", input[dir].packet.ID, input[dir].flitNr, ringCoord, input[dir].tempX, input[dir].tempY);
#endif
                    endCount++;
                    if (linkOut[dir] == null)
                    {
                        throw new Exception(String.Format("connector {0} does not have link in dir {1}",
                                                          ringCoord, dir));
                    }
                    linkOut[dir].In = input[dir];
                }
            }
            if (endCount != tempCount)
            {
                throw new Exception(String.Format("connector {0} created or destroyed flits.  Before: {1} | After: {2}", ringCoord, tempCount, endCount));
            }
        }