Moving around path weight tagging. Now CcnxFace owns metric field, which is used for tagging.

Correcting bugs in blackhole-sprint scenario.  This time it should be
the right one:
- instead of a hijacker app, all faces on hijacked node are turned down
- there was a trick with RTT estimation (when batch, it is necessary to
  reset history upon a new batch)
- instead of random runs, trying all possible combinations of
  producer/hijacker
diff --git a/examples/base-experiment.h b/examples/base-experiment.h
index fd8c1f0..c77760d 100644
--- a/examples/base-experiment.h
+++ b/examples/base-experiment.h
@@ -87,6 +87,8 @@
         // // Populate FIB based on IPv4 global routing controller
         ccnxHelper.InstallRoutesToAll ();
       }
+    
+    reader->ApplyOspfMetric ();
   }
   
   void InstallIpStack ()
@@ -94,6 +96,7 @@
     InternetStackHelper stack;
     stack.Install (reader->GetNodes ());
     reader->AssignIpv4Addresses (Ipv4Address ("10.0.0.0"));
+    reader->ApplyOspfMetric ();
 
     Ipv4GlobalRoutingHelper::PopulateRoutingTables ();
   }
@@ -132,6 +135,29 @@
   }
 
   void
+  SetPair (uint32_t pairId)
+  {
+    m_pairs.clear ();
+    m_usedNodes.clear ();
+
+    uint32_t i = 0;
+    for (uint32_t node1_num = 0; node1_num < 52; node1_num++)
+      for (uint32_t node2_num = 0; node2_num < 52; node2_num++)
+        {
+          if (node1_num == node2_num) continue;
+
+          // std::cout << "i = " << i << ", pairId = " << pairId << "\n";
+          if (i++ != pairId) continue;
+          
+          m_usedNodes.insert (node1_num);
+          m_usedNodes.insert (node2_num);
+
+          m_pairs.push_back (make_tuple (node1_num, node2_num));
+          return;
+        }
+  }
+
+  void
   Run (const Time &finishTime)
   {
     cout << "Run Simulation.\n";
diff --git a/examples/blackhole-sprint.cc b/examples/blackhole-sprint.cc
index 3901d70..d4884d5 100644
--- a/examples/blackhole-sprint.cc
+++ b/examples/blackhole-sprint.cc
@@ -240,6 +240,19 @@
     return d[destinationNode];
   }
 
+  // hijacker is more than an application. just disable all faces
+  static void
+  InstallHijacker (std::string prefix, Ptr<Node> node)
+  {
+    Ptr<Ccnx> ccnx = node->GetObject<Ccnx> ();
+    for (uint32_t i = 0; i < ccnx->GetNFaces (); i++)
+      {
+        Ptr<CcnxFace> face = ccnx->GetFace (i);
+        face->SetUp (false);
+      }
+    CcnxStackHelper::InstallRouteTo (prefix, node);
+  }
+
   //We are creating 10 pairs of producer-hijacker and everybody else is a consumer
   ApplicationContainer
   AddApplications ()
@@ -271,23 +284,12 @@
         apps.Add
           (legitimateProducerHelper.Install (node1));
         
-        CcnxAppHelper fakeProducerHelper ("ns3::CcnxHijacker");
-        fakeProducerHelper.SetPrefix (prefix);
-        ApplicationContainer hijacker = fakeProducerHelper.Install (node2);
-        apps.Add (hijacker);
-        hijacker.Start (Seconds(1.0));
-        
         // one more trick. Need to install route to hijacker (aka "hijacker announces itself as a legitimate producer")
         CcnxStackHelper::InstallRouteTo (prefix, node1);
-        Simulator::Schedule (Seconds(1.0), CcnxStackHelper::InstallRouteTo, prefix, node2);
-        // CcnxStackHelper::InstallRouteTo (prefix, node2);
+        Simulator::Schedule (Seconds(10.0), Experiment::InstallHijacker, prefix, node2);
 
         prefixes.push_back (prefix); // remember prefixes that consumers will be requesting
       }
-
-    // All consumers request exactly 10 packets, to convert number interests packets to requested size:
-    // size = 1040 * (max_number_of_packets-1) / 1024 / 1024
-    // double requestSize = 1040.0 * (10 - 1) / 1024.0 / 1024.0;
     
     // Create Consumers
     NodeContainer nodes = reader->GetNodes ();
@@ -299,7 +301,7 @@
 
         CcnxAppHelper consumerHelper ("ns3::CcnxConsumerBatches");
         consumerHelper.SetAttribute ("LifeTime", StringValue("100s"));
-        consumerHelper.SetAttribute ("Batches", StringValue("0s 10 0.5s 1 2s 1"));
+        consumerHelper.SetAttribute ("Batches", StringValue("0s 10 6s 1 20s 1"));
         BOOST_FOREACH (const string &prefix, prefixes)
           {
             consumerHelper.SetPrefix (prefix + "/" + lexical_cast<string> (namedId)); // make sure we're requesting unique prefixes... this was a huge bug before                 
@@ -344,7 +346,8 @@
       cout << "seed = " << SeedManager::GetSeed () << ", run = " << SeedManager::GetRun () << endl;
 
       Experiment experiment;
-      experiment.GenerateRandomPairs (1);
+      // experiment.GenerateRandomPairs (1);
+      experiment.SetPair (run);
       experiment.ComputeShortestWeightsPath(1,12);
       experiment.ComputeShortestDelayPath(1,12);
       cout << "Run " << run << endl;
@@ -360,12 +363,9 @@
       // traceHelper.EnableRateL3All (prefix + "rate-trace.log");
       traceHelper.EnableSeqsAppAll ("ns3::CcnxConsumerBatches", prefix + "consumers-seqs.log");
 
-      traceHelper.EnablePathWeights (prefix + "weights.log");
+      // enable path weights some time from now (ensure that all faces are created)
+      Simulator::Schedule (Seconds (4.5), &CcnxTraceHelper::EnablePathWeights, &traceHelper, prefix + "weights.log");
       std::cout << "Total " << apps.GetN () << " applications\n";
-      for (ApplicationContainer::Iterator i = apps.Begin (); i != apps.End (); i++)
-        {
-          Simulator::Schedule (Seconds (0.45), &CcnxTraceHelper::WeightsConnect, &traceHelper, (*i)->GetNode (), *i);
-        }
 
       experiment.Run (Seconds(40.0));
     }