Moved net-anim from contrib
authorJosh Pelkey <jpelkey@gatech.edu>
Tue, 24 Nov 2009 10:16:58 -0500
changeset 5776 aae948449722
parent 5775 86ff2e00d4ea
child 5777 a7ca957db043
child 5812 bb8a3a22d015
Moved net-anim from contrib
CHANGES.html
RELEASE_NOTES
examples/animation/dumbbell-animation.cc
examples/animation/grid-animation.cc
examples/animation/star-animation.cc
examples/animation/waf
examples/animation/wscript
examples/csma/csma-star.cc
examples/tcp/star.cc
examples/wscript
src/contrib/net-anim/animation-interface.cc
src/contrib/net-anim/animation-interface.h
src/contrib/net-anim/node-location.cc
src/contrib/net-anim/node-location.h
src/contrib/net-anim/point-to-point-dumbbell-helper.cc
src/contrib/net-anim/point-to-point-dumbbell-helper.h
src/contrib/net-anim/point-to-point-grid-helper.cc
src/contrib/net-anim/point-to-point-grid-helper.h
src/contrib/net-anim/test-dumbbell.cc
src/contrib/net-anim/test-grid.cc
src/contrib/net-anim/wscript
src/contrib/wscript
src/helper/animation-interface.cc
src/helper/animation-interface.h
src/helper/canvas-location.cc
src/helper/canvas-location.h
src/helper/csma-helper.cc
src/helper/csma-helper.h
src/helper/csma-star-helper.cc
src/helper/csma-star-helper.h
src/helper/point-to-point-dumbbell-helper.cc
src/helper/point-to-point-dumbbell-helper.h
src/helper/point-to-point-grid-helper.cc
src/helper/point-to-point-grid-helper.h
src/helper/point-to-point-helper.cc
src/helper/point-to-point-helper.h
src/helper/point-to-point-star-helper.cc
src/helper/point-to-point-star-helper.h
src/helper/wscript
src/wscript
--- a/CHANGES.html	Tue Nov 24 14:00:39 2009 +0100
+++ b/CHANGES.html	Tue Nov 24 10:16:58 2009 -0500
@@ -64,6 +64,12 @@
 <li><b>Ipv4::IsDestinationAddress (Ipv4Address address, uint32_t iif)</b> Method added to support checks of whether a destination address should be accepted 
 as one of the host's own addresses.  RFC 1122 Strong/Weak end system behavior can be changed with a new attribute (WeakEsModel) in class Ipv4.  </li>
 
+<li><b>Net-anim interface</b>: Provides an inteface to net-anim, a network animator for point-to-point 
+links in ns-3.  The interface generates a custom trace file for use with the NetAnim program.
+
+<li><b>Topology Helpers</b>: New topology helpers have been introduced including PointToPointStarHelper, 
+PointToPointDumbbellHelper, PointToPointGridHelper, and CsmaStarHelper.
+
 </ul>
 
 <h2>Changes to existing API:</h2>
@@ -128,7 +134,37 @@
 </pre>
 
 <li> Extensions to IPv4 <b>Ping</b> application: verbose output and the ability to configure different ping 
-sizes and time intervals (via new attributes)</li>
+sizes and time intervals (via new attributes)
+
+<li><b>Topology Helpers</b>: Previously, topology helpers such as a point-to-point star existed in the 
+PointToPointHelper class in the form of a method (ex: PointToPointHelper::InstallStar).  These topology 
+helpers have been pulled out of the specific helper classes and created as separate classes.  Several 
+different topology helper classes now exist including PointToPointStarHelper, PointToPointGridHelper, 
+PointToPointDumbbellHelper, and CsmaStarHelper.  For example, a user wishes to create a 
+point-to-point star network:<br>
+Before:
+<pre>
+NodeContainer hubNode;
+NodeContainer spokeNodes;
+hubNode.Create (1);
+Ptr<Node> hub = hubNode.Get (0);
+spokeNodes.Create (nNodes - 1);
+
+PointToPointHelper pointToPoint;
+pointToPoint.SetDeviceAttribute ("DataRate", StringValue ("5Mbps"));
+pointToPoint.SetChannelAttribute ("Delay", StringValue ("2ms"));
+NetDeviceContainer hubDevices, spokeDevices;
+pointToPoint.InstallStar (hubNode.Get (0), spokeNodes, hubDevices, spokeDevices);
+</pre>
+After:
+<pre>
+PointToPointHelper pointToPoint;
+pointToPoint.SetDeviceAttribute ("DataRate", StringValue ("5Mbps"));
+pointToPoint.SetChannelAttribute ("Delay", StringValue ("2ms"));
+PointToPointStarHelper star (nSpokes, pointToPoint);
+</pre>
+
+</li>
 
 </ul>
 
--- a/RELEASE_NOTES	Tue Nov 24 14:00:39 2009 +0100
+++ b/RELEASE_NOTES	Tue Nov 24 10:16:58 2009 -0500
@@ -36,6 +36,16 @@
 
   b) Ad hoc On-Demand Distance Vector (AODV) routing model according to RFC 3561. 
 
+  c) Net-anim:
+     - interface for animation of point-to-point links.
+     - dumbbell, grid, and star examples in examples/animation
+
+  d) Topology Helper classes:
+     - PointToPointDumbbellHelper
+     - PointToPointGridHelper
+     - PointToPointStarHelper
+     - CsmaStarHelper
+
 API changes from ns-3.6
 -----------------------
 API changes for this release are documented in the file CHANGES.html. 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/examples/animation/dumbbell-animation.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,118 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: George F. Riley<riley@ece.gatech.edu>
+ */
+
+#include <iostream>
+
+#include "ns3/core-module.h"
+#include "ns3/simulator-module.h"
+#include "ns3/node-module.h"
+#include "ns3/helper-module.h"
+
+using namespace ns3;
+
+int main (int argc, char *argv[])
+{
+  Config::SetDefault ("ns3::OnOffApplication::PacketSize", UintegerValue (512));
+  Config::SetDefault ("ns3::OnOffApplication::DataRate", StringValue ("500kb/s"));
+
+  uint32_t    nLeftLeaf = 5;
+  uint32_t    nRightLeaf = 5;
+  uint32_t    nLeaf = 0; // If non-zero, number of both left and right
+  uint16_t    port = 0;  // If non zero, port to bind to for anim connection
+  std::string animFile;  // Name of file for animation output
+
+  CommandLine cmd;
+  cmd.AddValue ("nLeftLeaf", "Number of left side leaf nodes", nLeftLeaf);
+  cmd.AddValue ("nRightLeaf","Number of right side leaf nodes", nRightLeaf);
+  cmd.AddValue ("nLeaf",     "Number of left and right side leaf nodes", nLeaf);
+  cmd.AddValue ("port",      "Port Number for Remote Animation", port);
+  cmd.AddValue ("animFile",  "File Name for Animation Output", animFile);
+
+  cmd.Parse (argc,argv);
+  if (nLeaf > 0)
+    {
+      nLeftLeaf = nLeaf;
+      nRightLeaf = nLeaf;
+    }
+  
+  // Create the point-to-point link helpers
+  PointToPointHelper pointToPointRouter;
+  pointToPointRouter.SetDeviceAttribute  ("DataRate", StringValue ("10Mbps"));
+  pointToPointRouter.SetChannelAttribute ("Delay", StringValue ("1ms"));
+  PointToPointHelper pointToPointLeaf;
+  pointToPointLeaf.SetDeviceAttribute    ("DataRate", StringValue ("10Mbps"));
+  pointToPointLeaf.SetChannelAttribute   ("Delay", StringValue ("1ms"));
+
+  PointToPointDumbbellHelper d(nLeftLeaf, pointToPointLeaf,
+                   nRightLeaf, pointToPointLeaf,
+                   pointToPointRouter);
+
+  // Install Stack
+  InternetStackHelper stack;
+  d.InstallStack (stack);
+
+  // Assign IP Addresses
+  d.AssignIpv4Addresses (Ipv4AddressHelper ("10.1.1.0", "255.255.255.0"),
+                    Ipv4AddressHelper ("10.2.1.0", "255.255.255.0"),
+                    Ipv4AddressHelper ("10.3.1.0", "255.255.255.0"));
+  
+  // Install on/off app on all right side nodes
+  OnOffHelper clientHelper ("ns3::UdpSocketFactory", Address ());
+  clientHelper.SetAttribute 
+    ("OnTime", RandomVariableValue (UniformVariable (0, 1)));
+  clientHelper.SetAttribute 
+    ("OffTime", RandomVariableValue (UniformVariable (0, 1)));
+  ApplicationContainer clientApps;
+
+  for (uint32_t i = 0; i < d.RightCount (); ++i)
+    {
+      // Create an on/off app sending packets to the same leaf right side
+      AddressValue remoteAddress (InetSocketAddress (d.GetLeftIpv4Address (i), 1000));
+      clientHelper.SetAttribute ("Remote", remoteAddress);
+      clientApps.Add(clientHelper.Install (d.GetRight (i)));
+    }
+
+  clientApps.Start (Seconds (0.0));
+  clientApps.Stop (Seconds (10.0));
+
+  // Set the bounding box for animation
+  d.BoundingBox (1, 1, 10, 10);
+
+  // Create the animation object and configure for specified output
+  AnimationInterface anim;
+  if (port > 0)
+    {
+      anim.SetServerPort (port);
+    }
+  else if (!animFile.empty ())
+    {
+      anim.SetOutputFile (animFile);
+    }
+  anim.StartAnimation ();
+  
+  // Set up the acutal simulation
+  Ipv4GlobalRoutingHelper::PopulateRoutingTables ();
+
+  std::cout << "Running the simulation" << std::endl;
+  Simulator::Run ();
+  std::cout << "Destroying the simulation" << std::endl;
+  Simulator::Destroy ();
+  std::cout << "Stopping the animation" << std::endl;
+  anim.StopAnimation();
+  return 0;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/examples/animation/grid-animation.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,106 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: Josh Pelkey <jpelkey@gatech.edu>
+ */
+
+#include <iostream>
+
+#include "ns3/core-module.h"
+#include "ns3/simulator-module.h"
+#include "ns3/node-module.h"
+#include "ns3/helper-module.h"
+
+using namespace ns3;
+
+int main (int argc, char *argv[])
+{
+  Config::SetDefault ("ns3::OnOffApplication::PacketSize", UintegerValue (512));
+  Config::SetDefault ("ns3::OnOffApplication::DataRate", StringValue ("500kb/s"));
+
+  uint32_t xSize = 5;
+  uint32_t ySize = 5;
+  uint16_t port = 0;
+  std::string animFile;
+
+  CommandLine cmd;
+  cmd.AddValue ("xSize", "Number of rows of nodes", xSize);
+  cmd.AddValue ("ySize", "Number of columns of nodes", ySize);
+  cmd.AddValue ("port",  "Port Number for Remote Animation", port);
+  cmd.AddValue ("animFile",  "File Name for Animation Output", animFile);
+
+  cmd.Parse (argc,argv);
+  if (xSize < 1 || ySize < 1 || (xSize < 2 && ySize < 2))
+    {
+      NS_FATAL_ERROR ("Need more nodes for grid.");
+    }
+  
+  PointToPointHelper pointToPoint;
+  pointToPoint.SetDeviceAttribute ("DataRate", StringValue ("5Mbps"));
+  pointToPoint.SetChannelAttribute ("Delay", StringValue ("2ms"));
+
+  // Create Grid
+  PointToPointGridHelper grid (xSize, ySize, pointToPoint);
+
+  // Install stack on Grid
+  InternetStackHelper stack;
+  grid.InstallStack (stack);
+
+  // Assign Addresses to Grid
+  grid.AssignIpv4Addresses (Ipv4AddressHelper ("10.1.1.0", "255.255.255.0"),
+                            Ipv4AddressHelper ("10.2.1.0", "255.255.255.0"));
+
+
+  OnOffHelper clientHelper ("ns3::UdpSocketFactory", Address ());
+  clientHelper.SetAttribute 
+    ("OnTime", RandomVariableValue (ConstantVariable (1)));
+  clientHelper.SetAttribute 
+    ("OffTime", RandomVariableValue (ConstantVariable (0)));
+  ApplicationContainer clientApps;
+
+  // Create an on/off app sending packets
+  AddressValue remoteAddress (InetSocketAddress (grid.GetIpv4Address (xSize-1,ySize-1), 1000));
+  clientHelper.SetAttribute ("Remote", remoteAddress);
+  clientApps.Add (clientHelper.Install (grid.GetNode (0,0)));
+
+  clientApps.Start (Seconds (0.0));
+  clientApps.Stop (Seconds (1.5));
+
+  // Set the bounding box for animation
+  grid.BoundingBox (1, 1, 10, 10);
+
+  // Create the animation object and configure for specified output
+  AnimationInterface anim;
+  if (port > 0)
+    {
+      anim.SetServerPort (port);
+    }
+  else if (!animFile.empty ())
+    {
+      anim.SetOutputFile (animFile);
+    }
+  anim.StartAnimation ();
+  
+  // Set up the actual simulation
+  Ipv4GlobalRoutingHelper::PopulateRoutingTables ();
+
+  std::cout << "Running the simulation" << std::endl;
+  Simulator::Run ();
+  std::cout << "Destroying the simulation" << std::endl;
+  Simulator::Destroy ();
+  std::cout << "Stopping the animation" << std::endl;
+  anim.StopAnimation();
+  return 0;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/examples/animation/star-animation.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,134 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ */
+
+#include "ns3/core-module.h"
+#include "ns3/simulator-module.h"
+#include "ns3/node-module.h"
+#include "ns3/helper-module.h"
+
+// Network topology (default)
+//
+//        n2 n3 n4              .
+//         \ | /                .
+//          \|/                 .
+//     n1--- n0---n5            .
+//          /|\                 .
+//         / | \                .
+//        n8 n7 n6              .
+//
+
+
+using namespace ns3;
+
+NS_LOG_COMPONENT_DEFINE ("StarAnimation");
+
+int 
+main (int argc, char *argv[])
+{
+
+  //
+  // Set up some default values for the simulation.
+  //
+  Config::SetDefault ("ns3::OnOffApplication::PacketSize", UintegerValue (137));
+
+  // ??? try and stick 15kb/s into the data rate
+  Config::SetDefault ("ns3::OnOffApplication::DataRate", StringValue ("14kb/s"));
+
+  //
+  // Default number of nodes in the star.  Overridable by command line argument.
+  //
+  uint32_t nSpokes = 8;
+  uint32_t animPort = 0;
+  std::string animFile;
+
+  CommandLine cmd;
+  cmd.AddValue("nSpokes", "Number of spoke nodes to place in the star", nSpokes);
+  cmd.AddValue ("animPort",      "Port Number for Remote Animation", animPort);
+  cmd.AddValue ("animFile",  "File Name for Animation Output", animFile);
+
+  cmd.Parse (argc, argv);
+
+  NS_LOG_INFO ("Build star topology.");
+  PointToPointHelper pointToPoint;
+  pointToPoint.SetDeviceAttribute ("DataRate", StringValue ("5Mbps"));
+  pointToPoint.SetChannelAttribute ("Delay", StringValue ("2ms"));
+  PointToPointStarHelper star (nSpokes, pointToPoint);
+
+  NS_LOG_INFO ("Install internet stack on all nodes.");
+  InternetStackHelper internet;
+  star.InstallStack (internet);
+
+  NS_LOG_INFO ("Assign IP Addresses.");
+  star.AssignIpv4Addresses (Ipv4AddressHelper ("10.1.1.0", "255.255.255.0"));
+
+  NS_LOG_INFO ("Create applications.");
+  //
+  // Create a packet sink on the star "hub" to receive packets.  
+  // 
+  uint16_t port = 50000;
+  Address hubLocalAddress (InetSocketAddress (Ipv4Address::GetAny (), port));
+  PacketSinkHelper packetSinkHelper ("ns3::TcpSocketFactory", hubLocalAddress);
+  ApplicationContainer hubApp = packetSinkHelper.Install (star.GetHub ());
+  hubApp.Start (Seconds (1.0));
+  hubApp.Stop (Seconds (10.0));
+
+  //
+  // Create OnOff applications to send TCP to the hub, one on each spoke node.
+  //
+  OnOffHelper onOffHelper ("ns3::TcpSocketFactory", Address ());
+  onOffHelper.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1)));
+  onOffHelper.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0)));
+
+  ApplicationContainer spokeApps;
+
+  for (uint32_t i = 0; i < star.SpokeCount (); ++i)
+    {
+      AddressValue remoteAddress (InetSocketAddress (star.GetHubIpv4Address (i), port));
+      onOffHelper.SetAttribute ("Remote", remoteAddress);
+      spokeApps.Add (onOffHelper.Install (star.GetSpoke (i)));
+  }
+  spokeApps.Start (Seconds (1.0));
+  spokeApps.Stop (Seconds (10.0));
+
+  NS_LOG_INFO ("Enable static global routing.");
+  //
+  // Turn on global static routing so we can actually be routed across the star.
+  //
+  Ipv4GlobalRoutingHelper::PopulateRoutingTables ();
+
+  // Set the bounding box for animation
+  star.BoundingBox (1, 1, 10, 10);
+  
+  // Create the animation object and configure for specified output
+  AnimationInterface anim;
+  if (animPort > 0)
+    {
+      anim.SetServerPort (animPort);
+    }
+  else if (!animFile.empty ())
+    {
+      anim.SetOutputFile (animFile);
+    }
+  anim.StartAnimation ();
+
+  NS_LOG_INFO ("Run Simulation.");
+  Simulator::Run ();
+  Simulator::Destroy ();
+  NS_LOG_INFO ("Done.");
+
+  return 0;
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/examples/animation/waf	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,1 @@
+exec "`dirname "$0"`"/../../waf "$@"
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/examples/animation/wscript	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,14 @@
+## -*- Mode: python; py-indent-offset: 4; indent-tabs-mode: nil; coding: utf-8; -*-
+
+def build(bld):
+    obj = bld.create_ns3_program('dumbbell-animation',
+                                 ['point-to-point', 'internet-stack'])
+    obj.source = 'dumbbell-animation.cc'
+
+    obj = bld.create_ns3_program('grid-animation',
+                                 ['point-to-point', 'internet-stack'])
+    obj.source = 'grid-animation.cc'
+
+    obj = bld.create_ns3_program('star-animation',
+                                 ['point-to-point', 'internet-stack'])
+    obj.source = 'star-animation.cc'
--- a/examples/csma/csma-star.cc	Tue Nov 24 14:00:39 2009 +0100
+++ b/examples/csma/csma-star.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -58,26 +58,17 @@
   //
   // Default number of nodes in the star.  Overridable by command line argument.
   //
-  uint32_t nNodes = 7;
+  uint32_t nSpokes = 7;
 
   CommandLine cmd;
-  cmd.AddValue("nNodes", "Number of nodes to place in the star", nNodes);
+  cmd.AddValue("nSpokes", "Number of spoke nodes to place in the star", nSpokes);
   cmd.Parse (argc, argv);
 
-  NS_LOG_INFO ("Create nodes.");
-  NodeContainer hubNode;
-  NodeContainer spokeNodes;
-  hubNode.Create (1);
-  Ptr<Node> hub = hubNode.Get (0);
-  spokeNodes.Create (nNodes - 1);
-
+  NS_LOG_INFO ("Build star topology.");
   CsmaHelper csma;
   csma.SetChannelAttribute ("DataRate", StringValue ("100Mbps"));
   csma.SetChannelAttribute ("Delay", StringValue ("1ms"));
-
-  NS_LOG_INFO ("Build star topology.");
-  NetDeviceContainer hubDevices, spokeDevices;
-  csma.InstallStar (hubNode.Get (0), spokeNodes, hubDevices, spokeDevices);
+  CsmaStarHelper star (nSpokes, csma);
 
   NodeContainer fillNodes;
 
@@ -89,12 +80,11 @@
   NetDeviceContainer fillDevices;
 
   uint32_t nFill = 14;
-  for (uint32_t i = 0; i < spokeDevices.GetN (); ++i)
+  for (uint32_t i = 0; i < star.GetSpokeDevices ().GetN (); ++i)
     {
-      Ptr<Channel> channel = spokeDevices.Get (i)->GetChannel ();
+      Ptr<Channel> channel = star.GetSpokeDevices ().Get (i)->GetChannel ();
       Ptr<CsmaChannel> csmaChannel = channel->GetObject<CsmaChannel> ();
       NodeContainer newNodes;
-      NetDeviceContainer newDevices;
       newNodes.Create (nFill);
       fillNodes.Add (newNodes);
       fillDevices.Add (csma.Install (newNodes, csmaChannel));
@@ -102,39 +92,30 @@
 
   NS_LOG_INFO ("Install internet stack on all nodes.");
   InternetStackHelper internet;
-  internet.Install (NodeContainer (hubNode, spokeNodes, fillNodes));
+  star.InstallStack (internet);
+  internet.Install (fillNodes);
 
   NS_LOG_INFO ("Assign IP Addresses.");
-  Ipv4AddressHelper address;
+  star.AssignIpv4Addresses (Ipv4AddressHelper ("10.1.0.0", "255.255.255.0"));
 
   //
-  // Assign IPv4 interfaces and IP addresses to the devices we previously
-  // created.  Keep track of the resulting addresses, one for the addresses
-  // of the hub node, and one for addresses on the spoke nodes.  Despite the
-  // name of the class (Ipv4InterfaceContainer), what is visible to clients 
-  // is really the address not the interface.
+  // We assigned addresses to the logical hub and the first "drop" of the 
+  // CSMA network that acts as the spoke, but we also have a number of fill
+  // devices (nFill) also hanging off the CSMA network.  We have got to 
+  // assign addresses to them as well.  We put all of the fill devices into
+  // a single device container, so the first nFill devices are associated
+  // with the channel connected to spokeDevices.Get (0), the second nFill
+  // devices afe associated with the channel connected to spokeDevices.Get (1)
+  // etc.
   //
-  Ipv4InterfaceContainer hubAddresses;
-  Ipv4InterfaceContainer spokeAddresses;
-
-  for(uint32_t i = 0; i < spokeNodes.GetN (); ++i)
+  Ipv4AddressHelper address;
+  for(uint32_t i = 0; i < star.SpokeCount (); ++i)
   {
     std::ostringstream subnet;
     subnet << "10.1." << i << ".0";
     NS_LOG_INFO ("Assign IP Addresses for CSMA subnet " << subnet.str ());
-    address.SetBase (subnet.str ().c_str (), "255.255.255.0");
-    hubAddresses.Add (address.Assign (hubDevices.Get (i)));
-    spokeAddresses.Add (address.Assign (spokeDevices.Get (i)));
-    //
-    // We assigned addresses to the logical hub and the first "drop" of the 
-    // CSMA network that acts as the spoke, but we also have a number of fill
-    // devices (nFill) also hanging off the CSMA network.  We have got to 
-    // assign addresses to them as well.  We put all of the fill devices into
-    // a single device container, so the first nFill devices are associated
-    // with the channel connected to spokeDevices.Get (0), the second nFill
-    // devices afe associated with the channel connected to spokeDevices.Get (1)
-    // etc.
-    //
+    address.SetBase (subnet.str ().c_str (), "255.255.255.0", "0.0.0.3");
+
     for (uint32_t j = 0; j < nFill; ++j)
       {
         address.Assign (fillDevices.Get (i * nFill + j));
@@ -148,7 +129,7 @@
   uint16_t port = 50000;
   Address hubLocalAddress (InetSocketAddress (Ipv4Address::GetAny (), port));
   PacketSinkHelper packetSinkHelper ("ns3::TcpSocketFactory", hubLocalAddress);
-  ApplicationContainer hubApp = packetSinkHelper.Install (hubNode);
+  ApplicationContainer hubApp = packetSinkHelper.Install (star.GetHub ());
   hubApp.Start (Seconds (1.0));
   hubApp.Stop (Seconds (10.0));
 
@@ -161,11 +142,11 @@
 
   ApplicationContainer spokeApps;
 
-  for (uint32_t i = 0; i < spokeNodes.GetN (); ++i)
+  for (uint32_t i = 0; i < star.SpokeCount (); ++i)
     {
-      AddressValue remoteAddress (InetSocketAddress (hubAddresses.GetAddress (i), port));
+      AddressValue remoteAddress (InetSocketAddress (star.GetHubIpv4Address (i), port));
       onOffHelper.SetAttribute ("Remote", remoteAddress);
-      spokeApps.Add (onOffHelper.Install (spokeNodes.Get (i)));
+      spokeApps.Add (onOffHelper.Install (star.GetSpoke (i)));
     }
 
   spokeApps.Start (Seconds (1.0));
@@ -183,7 +164,7 @@
 
   for (uint32_t i = 0; i < fillNodes.GetN (); ++i)
     {
-      AddressValue remoteAddress (InetSocketAddress (hubAddresses.GetAddress (i / nFill), port));
+      AddressValue remoteAddress (InetSocketAddress (star.GetHubIpv4Address (i / nFill), port));
       onOffHelper.SetAttribute ("Remote", remoteAddress);
       fillApps.Add (onOffHelper.Install (fillNodes.Get (i)));
     }
--- a/examples/tcp/star.cc	Tue Nov 24 14:00:39 2009 +0100
+++ b/examples/tcp/star.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -51,52 +51,24 @@
   //
   // Default number of nodes in the star.  Overridable by command line argument.
   //
-  uint32_t nNodes = 9;
+  uint32_t nSpokes = 8;
 
   CommandLine cmd;
-  cmd.AddValue("nNodes", "Number of nodes to place in the star", nNodes);
+  cmd.AddValue("nSpokes", "Number of nodes to place in the star", nSpokes);
   cmd.Parse (argc, argv);
 
-  NS_LOG_INFO ("Create nodes.");
-  NodeContainer hubNode;
-  NodeContainer spokeNodes;
-  hubNode.Create (1);
-  Ptr<Node> hub = hubNode.Get (0);
-  spokeNodes.Create (nNodes - 1);
-
-  NS_LOG_INFO ("Install internet stack on all nodes.");
-  InternetStackHelper internet;
-  internet.Install (NodeContainer (hubNode, spokeNodes));
-
+  NS_LOG_INFO ("Build star topology.");
   PointToPointHelper pointToPoint;
   pointToPoint.SetDeviceAttribute ("DataRate", StringValue ("5Mbps"));
   pointToPoint.SetChannelAttribute ("Delay", StringValue ("2ms"));
+  PointToPointStarHelper star (nSpokes, pointToPoint);
 
-  NS_LOG_INFO ("Build star topology.");
-  NetDeviceContainer hubDevices, spokeDevices;
-  pointToPoint.InstallStar (hubNode.Get (0), spokeNodes, hubDevices, spokeDevices);
+  NS_LOG_INFO ("Install internet stack on all nodes.");
+  InternetStackHelper internet;
+  star.InstallStack (internet);
 
   NS_LOG_INFO ("Assign IP Addresses.");
-  Ipv4AddressHelper address;
-
-  //
-  // Assign IPv4 interfaces and IP addresses to the devices we previously
-  // created.  Keep track of the resulting addresses, one for the addresses
-  // of the hub node, and one for addresses on the spoke nodes.  Despite the
-  // name of the class, what is visible to clients is really the address.
-  //
-  Ipv4InterfaceContainer hubAddresses;
-  Ipv4InterfaceContainer spokeAddresses;
-
-  for(uint32_t i = 0; i < spokeNodes.GetN (); ++i)
-  {
-    std::ostringstream subnet;
-    subnet << "10.1.1." << (i << 2);
-    NS_LOG_INFO ("Assign IP Addresses for point-to-point subnet " << subnet.str ());
-    address.SetBase (subnet.str ().c_str (), "255.255.255.252");
-    hubAddresses.Add (address.Assign (hubDevices.Get (i)));
-    spokeAddresses.Add (address.Assign (spokeDevices.Get (i)));
-  }
+  star.AssignIpv4Addresses (Ipv4AddressHelper ("10.1.1.0", "255.255.255.0"));
 
   NS_LOG_INFO ("Create applications.");
   //
@@ -105,7 +77,7 @@
   uint16_t port = 50000;
   Address hubLocalAddress (InetSocketAddress (Ipv4Address::GetAny (), port));
   PacketSinkHelper packetSinkHelper ("ns3::TcpSocketFactory", hubLocalAddress);
-  ApplicationContainer hubApp = packetSinkHelper.Install (hubNode);
+  ApplicationContainer hubApp = packetSinkHelper.Install (star.GetHub ());
   hubApp.Start (Seconds (1.0));
   hubApp.Stop (Seconds (10.0));
 
@@ -118,11 +90,11 @@
 
   ApplicationContainer spokeApps;
 
-  for (uint32_t i = 0; i < spokeNodes.GetN (); ++i)
+  for (uint32_t i = 0; i < star.SpokeCount (); ++i)
     {
-      AddressValue remoteAddress (InetSocketAddress (hubAddresses.GetAddress (i), port));
+      AddressValue remoteAddress (InetSocketAddress (star.GetHubIpv4Address (i), port));
       onOffHelper.SetAttribute ("Remote", remoteAddress);
-      spokeApps.Add (onOffHelper.Install (spokeNodes.Get (i)));
+      spokeApps.Add (onOffHelper.Install (star.GetSpoke (i)));
   }
   spokeApps.Start (Seconds (1.0));
   spokeApps.Stop (Seconds (10.0));
--- a/examples/wscript	Tue Nov 24 14:00:39 2009 +0100
+++ b/examples/wscript	Tue Nov 24 10:16:58 2009 -0500
@@ -3,6 +3,7 @@
 def build(bld):
     env = bld.env_of_name('default')
     if env['ENABLE_EXAMPLES']:
+        bld.add_subdirs('animation')
         bld.add_subdirs('csma')
         bld.add_subdirs('emulation')
         bld.add_subdirs('error-model')
--- a/src/contrib/net-anim/animation-interface.cc	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,202 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: George F. Riley<riley@ece.gatech.edu>
- */
-
-// Interface between ns3 and the network animator
-
-#include <stdio.h>
-#include <sstream>
-
-#include "ns3/net-anim-config.h"
-
-// Socket related includes
-#if defined(HAVE_SYS_SOCKET_H) && defined(HAVE_NETINET_IN_H)
-# include <sys/socket.h>
-# include <netinet/in.h>
-#else
-#include <fcntl.h>
-#endif
-
-// ns3 includes
-#include "ns3/animation-interface.h"
-#include "ns3/channel.h"
-#include "ns3/config.h"
-#include "ns3/node.h"
-#include "ns3/node-location.h"
-#include "ns3/packet.h"
-#include "ns3/simulator.h"
-
-using namespace std;
-
-NS_LOG_COMPONENT_DEFINE ("AnimationInterface");
-
-namespace ns3 {
-
-AnimationInterface::AnimationInterface ()
-  : m_fHandle (STDOUT_FILENO), m_model (0)
-{
-}
-
-bool AnimationInterface::SetOutputFile (const std::string& fn)
-{
-  FILE* f = fopen (fn.c_str (), "w");
-  if (!f)
-    {
-      return false; // Can't open
-    }
-  m_fHandle = fileno (f); // Set the file handle
-  return true;
-}
-
-bool AnimationInterface::SetServerPort (uint16_t port)
-{
-#if defined(HAVE_SYS_SOCKET_H) && defined(HAVE_NETINET_IN_H)
-  int s = socket (AF_INET, SOCK_STREAM, 0);
-  struct sockaddr_in addr;
-  addr.sin_family = AF_INET;
-  addr.sin_port = htons (port);
-  addr.sin_addr.s_addr = htonl (INADDR_ANY);
-  if (bind (s, (struct sockaddr*)&addr, sizeof (addr)) < 0)
-    {
-      NS_LOG_WARN ("Can't bind to port " << port << ", exiting.");
-      return false;
-    }
-  listen (s, 1);
-  NS_LOG_INFO ("Waiting for animator connection");
-  // Now wait for the animator to connect in
-  m_fHandle = accept (s, 0, 0);
-  NS_LOG_INFO ("Got animator connection from remote");
-  // set the linger socket option
-  int t = 1;
-  setsockopt (s, SOL_SOCKET, SO_LINGER, &t, sizeof(t));
-  return true;
-#endif
-  return false;//never reached unless the above is disabled
-}
-
-bool AnimationInterface::SetInternalAnimation ()
-{
-  return false; // Not implemented yet
-}
-
-void AnimationInterface::StartAnimation ()
-{
-  // Dump the topology
-  for (NodeList::Iterator i = NodeList::Begin (); i != NodeList::End (); ++i)
-    {
-      Ptr<Node> n = *i;
-      Ptr<NodeLocation> loc = n->GetObject<NodeLocation> ();
-      if (loc)
-        {
-          // Location exists, dump it
-          Vector v = loc->GetLocation ();
-          ostringstream oss;
-          oss << "0.0 N " << n->GetId () 
-               << " " << v.x << " " << v.y << endl;
-          WriteN (m_fHandle, oss.str ().c_str (), oss.str ().length ());
-        }
-    }
-  // Now dump the p2p links
-  for (NodeList::Iterator i = NodeList::Begin (); i != NodeList::End(); ++i)
-    {
-      Ptr<Node> n = *i;
-      uint32_t n1Id = n->GetId ();
-      uint32_t nDev = n->GetNDevices ();  // Number of devices
-      for (uint32_t i = 0; i < nDev; ++i)
-        {
-          Ptr<NetDevice> dev = n->GetDevice (i);
-          Ptr<Channel>   ch = dev->GetChannel ();
-          if (!ch) 
-            {
-              continue; // No channel, can't be p2p device
-            }
-          string channelType = ch->GetInstanceTypeId ().GetName ();
-          if (channelType == string ("ns3::PointToPointChannel"))
-            { // Since these are duplex links, we only need to dump
-              // if srcid < dstid
-              uint32_t nChDev = ch->GetNDevices ();
-              for (uint32_t j = 0; j < nChDev; ++j)
-                {
-                  Ptr<NetDevice> chDev = ch->GetDevice (j);
-                  uint32_t n2Id = chDev->GetNode ()->GetId ();
-                  if (n1Id < n2Id)
-                    { // ouptut the p2p link
-                      ostringstream oss;
-                      oss << "0.0 L "  << n1Id << " " << n2Id << endl;
-                      WriteN (m_fHandle, oss.str ().c_str (),
-                             oss.str ().length ());
-                    }
-                }
-            }
-          else
-            {
-              NS_FATAL_ERROR ("Net animation currently only supports point-to-point links.");
-            }
-        }
-    }
-  
-  // Connect the callback for packet tx events
-  Config::Connect ("/ChannelList/*/TxRxPointToPoint",
-                   MakeCallback (&AnimationInterface::DevTxTrace, this));
-}
-
-void AnimationInterface::StopAnimation ()
-{
-  if (m_fHandle > 0) 
-    {
-      close (m_fHandle);
-    }
-}
-
-
-// Private methods
-int AnimationInterface::WriteN (int h, const char* data, uint32_t count)
-{ // Write count bytes to h from data
-  uint32_t    nLeft   = count;
-  const char* p       = data;
-  uint32_t    written = 0;
-
-  while (nLeft)
-    {
-      int n = write (h, p, nLeft);
-      if (n <= 0) 
-        {
-          return written;
-        }
-      written += n;
-      nLeft -= n;
-      p += n;
-    }
-  return written;
-}
-  
-void AnimationInterface::DevTxTrace (std::string context, Ptr<const Packet> p,
-                                     Ptr<NetDevice> tx, Ptr<NetDevice> rx,
-                                     Time txTime, Time rxTime)
-{
-  Time now = Simulator::Now ();
-  ostringstream oss;
-  oss << now.GetSeconds() << " P "
-      << tx->GetNode ()->GetId () << " "
-      << rx->GetNode ()->GetId () << " "
-      << (now + txTime).GetSeconds () << " " // last bit tx time
-      << (now + rxTime - txTime).GetSeconds() << " "  // first bit rx time
-      << (now + rxTime).GetSeconds () << endl;         // last bit rx time
-  WriteN (m_fHandle, oss.str ().c_str (), oss.str ().length ());
-}
-
-} // namespace ns3
--- a/src/contrib/net-anim/animation-interface.h	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,120 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: George F. Riley<riley@ece.gatech.edu>
- */
-
-// Interface between ns3 and the network animator
-
-#ifndef __ANIMATION_INTERFACE__H__
-#define __ANIMATION_INTERFACE__H__
-
-#include <string>
-
-#include "ns3/ptr.h"
-#include "ns3/net-device.h"
-#include "ns3/nstime.h"
-#include "ns3/log.h"
-#include "ns3/node-list.h"
-
-
-namespace ns3 {
-class NetModel;
-
-/**
- * \brief Interface to network animator
- *
- * Provides functions that facilitate communications with an
- * external or internal network animator.
- */
-class AnimationInterface
-{
-public:
-/**
- * @brief Construct the animator interface. No arguments needed.
- */
-  AnimationInterface ();
-/**
- * @brief Specify that animation commands are to be written
- * to the specified output file.
- *
- * This call is used to write the animation information to a text
- * file that can later be used as input to the network animator tool.
- *
- * @param fn The name of the output file.
- * @returns true if successful open.
- */
-  bool SetOutputFile (const std::string& fn);
-
-/**
- * @brief Specify that animation commands are to be written to
- * a socket.
- *
- * This call is used to set the ns3 process in server mode, waiting
- * for a TCP connection from the animator.  This call will not
- * return until the animator connects in, or if the bind to the
- * specified port fails.
- *
- * @param port Port number to bind to.
- * @returns true if connection created, false if bind failed.
- */
-  bool SetServerPort (uint16_t port);
-
-/**
- * @brief Specify that animation window is to be created as part
- * of the ns3 process.
- *
- * This call is used to set the ns3 animator internal to the
- * current process.  This will fail if the ns3 library was built
- * without the QT4 developer packages.
- *
- * @returns true if animation started, false if failed.
- */
-  bool SetInternalAnimation ();
-
-/**
- * @brief Writes the topology information and sets up the appropriate
- *  animation packet tx callback
- *
- * Writes the topology information to the appropriate output, depending
- * on prior calls to SetOutputFile, SetServerPort, or SetInternalAnimation.
- * Then creates the callbacks needed for the animator to start processing
- * packets.
- *
- */
-  void StartAnimation ();
-
-/**
- * @brief Closes the interface to the animator.
- *
- */
-  void StopAnimation ();
-
-
-private:
-  // Packet tx animation callback
-  void DevTxTrace (std::string context, Ptr<const Packet> p,
-                 Ptr<NetDevice> tx, Ptr<NetDevice> rx,
-                 Time txTime, Time rxTime);
-  // Write specified amount of data to the specified handle
-  int  WriteN (int, const char*, uint32_t);
-private:
-  int       m_fHandle;  // File handle for output (-1 if none)
-  NetModel* m_model;    // If non nil, points to the internal network model
-                        // for the interlan animator
-};
-}
-#endif
-
--- a/src/contrib/net-anim/node-location.cc	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,56 +0,0 @@
-/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
-/*
- * Copyright (c) 2009 Georgia Institute of Technology
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: George Riley<riley@ece.gatech.edu>
- */
-
-#include "node-location.h"
-
-namespace ns3 {
-
-TypeId 
-NodeLocation::GetTypeId (void)
-{
-  static TypeId tid = TypeId ("ns3::NodeLocation")
-    .SetParent<Object> ()
-    .AddAttribute ("Position", "The current position of the mobility model.",
-                   TypeId::ATTR_SET | TypeId::ATTR_GET,
-                   VectorValue (Vector (0.0, 0.0, 0.0)),
-                   MakeVectorAccessor (&NodeLocation::SetLocation,
-                                        &NodeLocation::GetLocation),
-                   MakeVectorChecker ())
-    ;
-  return tid;
-}
-
-NodeLocation::NodeLocation ()
-{}
-
-NodeLocation::~NodeLocation ()
-{}
-
-Vector NodeLocation::GetLocation (void) const
-{
-  return m_location;
-}
-
-void NodeLocation::SetLocation (const Vector &location)
-{
-  m_location = location;
-}
-
-} // namespace ns3
--- a/src/contrib/net-anim/node-location.h	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,61 +0,0 @@
-/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
-/*
- * Copyright (c) 2009 Georgia Institute of Technology
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: George Riley<riley@ece.gatech.edu>
- */
-#ifndef __NODE_LOCATION_H__
-#define __NODE_LOCATION_H__
-
-#include "ns3/object.h"
-#include "ns3/traced-callback.h"
-#include "ns3/vector.h"
-
-namespace ns3 {
-
-/**
- * \brief Keep track of the current location of an object
- *
- * This can be used anytime a logical node location is needed
- * (as opposed to a physical location used by the wireless PHY
- * layer to calculate path loss).  One potential use of 
- * this is by the animator to determine where to position the
- * node icon on the animation display.  Location units are 
- * arbitrary and dimensionless.  In the case of use by the
- * animator they dimensions are in pixels.
- */
-class NodeLocation : public Object
-{
-public:
-  static TypeId GetTypeId (void);
-  NodeLocation ();
-  virtual ~NodeLocation ();
-
-  /**
-   * \returns the current location
-   */
-  Vector GetLocation (void) const;
-  /**
-   * \param location the location to set.
-   */
-  void SetLocation (const Vector &location);
-private:
-  Vector m_location;
-};
-
-}; // namespace ns3
-
-#endif /* __NODE_LOCATION_H__ */
--- a/src/contrib/net-anim/point-to-point-dumbbell-helper.cc	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,249 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: George F. Riley<riley@ece.gatech.edu>
- */
-
-// Implement an object to create a dumbbell topology.
-
-#include <iostream>
-#include <sstream>
-
-// ns3 includes
-#include "ns3/animation-interface.h"
-#include "ns3/point-to-point-dumbbell-helper.h"
-#include "ns3/node-location.h"
-
-#include "ns3/node-list.h"
-#include "ns3/point-to-point-net-device.h"
-#include "ns3/vector.h"
-
-using namespace std;
-
-NS_LOG_COMPONENT_DEFINE("PointToPointDumbbellHelper");
-
-namespace ns3 {
-  
-PointToPointDumbbellHelper::PointToPointDumbbellHelper (uint32_t nLeftLeaf,
-                   PointToPointHelper& leftHelper,
-                   uint32_t nRightLeaf,
-                   PointToPointHelper& rightHelper,
-                   PointToPointHelper& bottleneckHelper)
-{
-  // Create the bottleneck routers
-  m_routers.Create (2);
-  // Create the leaf nodes
-  m_leftLeaf.Create (nLeftLeaf);
-  m_rightLeaf.Create (nRightLeaf);
-
-  // Add the link connecting routers
-  m_routerDevices = bottleneckHelper.Install (m_routers);
-  // Add the left side links
-  for (uint32_t i = 0; i < nLeftLeaf; ++i)
-    {
-      NetDeviceContainer c = leftHelper.Install (m_routers.Get (0),
-                                                m_leftLeaf.Get (i));
-      m_leftRouterDevices.Add (c.Get (0));
-      m_leftLeafDevices.Add (c.Get(1));
-    }
-  // Add the right side links
-  for (uint32_t i = 0; i < nRightLeaf; ++i)
-    {
-      NetDeviceContainer c = rightHelper.Install (m_routers.Get (1),
-                                                m_rightLeaf.Get (i));
-      m_rightRouterDevices.Add (c.Get (0));
-      m_rightLeafDevices.Add (c.Get (1));
-    }
-}
-
-Ptr<Node> PointToPointDumbbellHelper::GetLeft () const
-{ // Get the left side bottleneck router
-  return m_routers.Get (0);
-}
-
-Ptr<Node> PointToPointDumbbellHelper::GetLeft (uint32_t i) const
-{ // Get the i'th left side leaf
-  return m_leftLeaf.Get (i);
-}
-
-Ptr<Node> PointToPointDumbbellHelper::GetRight () const
-{ // Get the right side bottleneck router
-  return m_routers.Get (1);
-}
-
-Ptr<Node> PointToPointDumbbellHelper::GetRight (uint32_t i) const
-{ // Get the i'th right side leaf
-  return m_rightLeaf.Get (i);
-}
-
-Ipv4Address PointToPointDumbbellHelper::GetLeftAddress (uint32_t i) const
-{
-  return m_leftLeafInterfaces.GetAddress (i);
-}
-
-Ipv4Address PointToPointDumbbellHelper::GetRightAddress (uint32_t i) const
-{
-  return m_rightLeafInterfaces.GetAddress (i);
-}
-
-uint32_t  PointToPointDumbbellHelper::LeftCount () const
-{ // Number of left side nodes
-  return m_leftLeaf.GetN ();
-}
-
-uint32_t  PointToPointDumbbellHelper::RightCount () const
-{ // Number of right side nodes
-  return m_rightLeaf.GetN ();
-}
-
-void PointToPointDumbbellHelper::InstallStack (InternetStackHelper stack)
-{
-  stack.Install (m_routers);
-  stack.Install (m_leftLeaf);
-  stack.Install (m_rightLeaf);
-}
-
-void PointToPointDumbbellHelper::AssignAddresses (Ipv4AddressHelper leftIp,
-                               Ipv4AddressHelper rightIp,
-                               Ipv4AddressHelper routerIp)
-{
-  // Assign the router network
-  m_routerInterfaces = routerIp.Assign (m_routerDevices);
-  // Assign to left side 
-  for (uint32_t i = 0; i < LeftCount (); ++i)
-    {
-      NetDeviceContainer ndc;
-      ndc.Add (m_leftLeafDevices.Get (i));
-      ndc.Add (m_leftRouterDevices.Get (i));
-      Ipv4InterfaceContainer ifc = leftIp.Assign(ndc);
-      m_leftLeafInterfaces.Add (ifc.Get (0));
-      m_leftRouterInterfaces.Add (ifc.Get (1));
-      leftIp.NewNetwork ();
-    }
-  // Assign to right size
-  for (uint32_t i = 0; i < RightCount (); ++i)
-    {
-      NetDeviceContainer ndc;
-      ndc.Add (m_rightLeafDevices.Get (i));
-      ndc.Add (m_rightRouterDevices.Get (i));
-      Ipv4InterfaceContainer ifc = rightIp.Assign (ndc);
-      m_rightLeafInterfaces.Add (ifc.Get (0));
-      m_rightRouterInterfaces.Add (ifc.Get (1));
-      rightIp.NewNetwork ();
-    }
-}
-
-
-void PointToPointDumbbellHelper::BoundingBox (double ulx, double uly, // Upper left x/y
-                           double lrx, double lry) // Lower right y
-{
-  double xDist = lrx - ulx;
-  double yDist = lry - uly;
-  double xAdder = xDist / 3.0;
-  double  thetaL = M_PI / (LeftCount () + 1.0);
-  double  thetaR = M_PI / (RightCount () + 1.0);
-
-  // Place the left router
-  Ptr<Node> lr = GetLeft ();
-  Ptr<NodeLocation> loc = lr->GetObject<NodeLocation> ();
-  if (loc == 0)
-    {
-      loc = CreateObject<NodeLocation> ();
-      lr->AggregateObject (loc);
-    }
-  Vector lrl (ulx + xAdder, uly + yDist/2.0, 0);
-  loc->SetLocation (lrl);
-  
-  // Place the right router
-  Ptr<Node> rr = GetRight ();
-  loc = rr->GetObject<NodeLocation> ();
-  if (loc == 0)
-    {
-      loc = CreateObject<NodeLocation> ();
-      rr->AggregateObject (loc);
-    }
-  Vector rrl (ulx + xAdder * 2, uly + yDist/2.0, 0); // Right router location
-  loc->SetLocation (rrl);
-
-  // Place the left leaf nodes
-  double theta = -M_PI_2 + thetaL;
-  for (uint32_t l = 0; l < LeftCount (); ++l)
-    {
-      // Make them in a circular pattern to make all line lengths the same
-      // Special case when theta = 0, to be sure we get a straight line
-      if ((LeftCount () % 2) == 1)
-        { // Count is odd, see if we are in middle
-          if (l == (LeftCount () / 2))
-            {
-              theta = 0.0;
-            }
-        }
-      Ptr<Node> ln = GetLeft (l);
-      loc = ln->GetObject<NodeLocation> ();
-      if (loc == 0)
-        {
-          loc = CreateObject<NodeLocation> ();
-          ln->AggregateObject (loc);
-        }
-      Vector lnl (lrl.x - cos (theta) * xAdder,
-                   lrl.y + sin (theta) * xAdder, 0);  // Left Node Location
-      // Insure did not exceed bounding box
-      if (lnl.y < uly) 
-        {
-          lnl.y = uly; // Set to upper right y
-        }
-      if (lnl.y > lry) 
-        {
-          lnl.y = lry; // Set to lower right y
-        }
-      loc->SetLocation (lnl);
-      theta += thetaL;
-    }
-  // Place the right nodes
-  theta = -M_PI_2 + thetaR;
-  for (uint32_t r = 0; r < RightCount (); ++r)
-    {
-      // Special case when theta = 0, to be sure we get a straight line
-      if ((RightCount () % 2) == 1)
-        { // Count is odd, see if we are in middle
-          if (r == (RightCount () / 2))
-            {
-              theta = 0.0;
-            }
-        }
-      Ptr<Node> rn = GetRight (r);
-      loc = rn->GetObject<NodeLocation> ();
-      if (loc == 0)
-        {
-          loc = CreateObject<NodeLocation> ();
-          rn->AggregateObject (loc);
-        }
-      Vector rnl (rrl.x + cos (theta) * xAdder, // Right node location
-                   rrl.y + sin (theta) * xAdder, 0);
-      // Insure did not exceed bounding box
-      if (rnl.y < uly) 
-        {
-          rnl.y = uly; // Set to upper right y
-        }
-      if (rnl.y > lry) 
-        {
-          rnl.y = lry; // Set to lower right y
-        }
-      loc->SetLocation (rnl);
-      theta += thetaR;
-    }
-}
-  
-} // namespace ns3
--- a/src/contrib/net-anim/point-to-point-dumbbell-helper.h	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,77 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: George F. Riley<riley@ece.gatech.edu>
- */
-
-// Define an object to create a dumbbell topology.
-
-#ifndef __POINT_TO_POINT_DUMBBELL_HELPER_H__
-#define __POINT_TO_POINT_DUMBBELL_HELPER_H__
-
-#include <string>
-
-#include "point-to-point-helper.h"
-#include "ipv4-address-helper.h"
-#include "internet-stack-helper.h"
-#include "ipv4-interface-container.h"
-
-namespace ns3 {
-  
-class PointToPointDumbbellHelper
-{
-public:
-  PointToPointDumbbellHelper (uint32_t nLeftLeaf,  // Number of left size leaf nodes
-           PointToPointHelper& leftHelper,
-           uint32_t nRightLeaf, // Number of right side leaf nodes
-           PointToPointHelper& rightHelper,
-           PointToPointHelper& bottleneckHelper);
-public:
-  Ptr<Node> GetLeft ()           const; // Get the left side bottleneck router
-  Ptr<Node> GetLeft (uint32_t)   const; // Get the i'th left side leaf
-  Ptr<Node> GetRight ()          const; // Get the right side bottleneck router
-  Ptr<Node> GetRight (uint32_t)  const; // Get the i'th right side leaf
-  Ipv4Address GetLeftAddress (uint32_t)  const; // Get left leaf address
-  Ipv4Address GetRightAddress (uint32_t) const; // Get right leaf address
-  uint32_t  LeftCount ()         const; // Number of left side nodes
-  uint32_t  RightCount ()        const; // Number of right side nodes
-  void      InstallStack (InternetStackHelper stack);
-  void      AssignAddresses (Ipv4AddressHelper leftIp,
-                            Ipv4AddressHelper rightIp,
-                            Ipv4AddressHelper routerIp);
-  // Add locations in the specified bounding box
-  // Arguments are uppler left x, upper left y, lower right x, lower right y
-  void      BoundingBox (double, double, double, double);
-  
-private:
-  NodeContainer          m_leftLeaf;
-  NetDeviceContainer     m_leftLeafDevices;
-  NodeContainer          m_rightLeaf;
-  NetDeviceContainer     m_rightLeafDevices;
-  NodeContainer          m_routers;
-  NetDeviceContainer     m_routerDevices; // just two connecting the routers
-  // Device containers for the router devices connecting to the leaf devices
-  NetDeviceContainer     m_leftRouterDevices;
-  NetDeviceContainer     m_rightRouterDevices;
-  Ipv4InterfaceContainer m_leftLeafInterfaces;
-  Ipv4InterfaceContainer m_leftRouterInterfaces;
-  Ipv4InterfaceContainer m_rightLeafInterfaces;
-  Ipv4InterfaceContainer m_rightRouterInterfaces;
-  Ipv4InterfaceContainer m_routerInterfaces;
-};
-}
-#endif
-
-
--- a/src/contrib/net-anim/point-to-point-grid-helper.cc	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,180 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: Josh Pelkey <jpelkey@gatech.edu>
- */
-
-#include "ns3/point-to-point-grid-helper.h"
-#include "ns3/animation-interface.h"
-#include "ns3/internet-stack-helper.h"
-#include "ns3/point-to-point-helper.h"
-#include "ns3/node-location.h"
-#include "ns3/string.h"
-#include "ns3/vector.h"
-#include "ns3/log.h"
-
-NS_LOG_COMPONENT_DEFINE("PointToPointGridHelper");
-
-namespace ns3 {
-  
-PointToPointGridHelper::PointToPointGridHelper (uint32_t nRows, 
-                                                uint32_t nCols, 
-                                                PointToPointHelper pointToPoint)
-  : m_xSize (nCols), m_ySize (nRows)
-{
-  InternetStackHelper stack;
-
-  for (uint32_t y = 0; y < nRows; ++y)
-  {
-    NodeContainer rowNodes;
-    NetDeviceContainer rowDevices;
-    NetDeviceContainer colDevices;
-
-    for (uint32_t x = 0; x < nCols; ++x)
-    {
-      rowNodes.Create(1);
-
-      // install p2p links across the row
-      if (x > 0)
-      {
-        rowDevices.Add (pointToPoint.
-            Install (rowNodes.Get (x-1), rowNodes.Get (x)));
-      }
-
-      // install vertical p2p links
-      if (y > 0)
-      {
-        colDevices.Add(pointToPoint.
-                      Install ((m_nodes.at (y-1)).Get (x), rowNodes.Get (x)));
-      }
-    }
-
-    m_nodes.push_back(rowNodes);
-    m_rowDevices.push_back (rowDevices);
-
-    if (y > 0)
-      m_colDevices.push_back (colDevices);
-  }
-}
-
-void
-PointToPointGridHelper::InstallStack (InternetStackHelper stack)
-{
-  for (uint32_t i = 0; i < m_nodes.size (); ++i)
-    {
-      NodeContainer rowNodes = m_nodes[i];
-      for (uint32_t j = 0; j < rowNodes.GetN (); ++j)
-        {
-          stack.Install (rowNodes.Get (j));
-        }
-    }
-}
-
-void
-PointToPointGridHelper::AssignAddresses (Ipv4AddressHelper rowIp, Ipv4AddressHelper colIp)
-{
-  // Assign addresses to all row devices in the grid.
-  // These devices are stored in a vector.  Each row 
-  // of the grid has all the row devices in one entry 
-  // of the vector.  These entries come in pairs.
-  for (uint32_t i = 0; i < m_rowDevices.size (); ++i)
-    {
-      Ipv4InterfaceContainer rowInterfaces; 
-      NetDeviceContainer rowContainer = m_rowDevices[i];
-      for (uint32_t j = 0; j < rowContainer.GetN (); j+=2)
-        {
-          rowInterfaces.Add (rowIp.Assign (rowContainer.Get (j))); 
-          rowInterfaces.Add (rowIp.Assign (rowContainer.Get (j+1)));
-          rowIp.NewNetwork ();
-        }
-      m_rowInterfaces.push_back (rowInterfaces);
-    }
-
-  // Assign addresses to all col devices in the grid.
-  // These devices are stored in a vector.  Each col 
-  // of the grid has all the col devices in one entry 
-  // of the vector.  These entries come in pairs.
-  for (uint32_t i = 0; i < m_colDevices.size (); ++i)
-    {
-      Ipv4InterfaceContainer colInterfaces; 
-      NetDeviceContainer colContainer = m_colDevices[i];
-      for (uint32_t j = 0; j < colContainer.GetN (); j+=2)
-        {
-          colInterfaces.Add (colIp.Assign (colContainer.Get (j))); 
-          colInterfaces.Add (colIp.Assign (colContainer.Get (j+1)));
-          colIp.NewNetwork ();
-        }
-      m_colInterfaces.push_back (colInterfaces);
-    }
-}
-
-void
-PointToPointGridHelper::BoundingBox (double ulx, double uly,
-                         double lrx, double lry)
-{
-  double xDist = lrx - ulx;
-  double yDist = lry - uly;
-
-  double xAdder = xDist / m_xSize;
-  double yAdder = yDist / m_ySize;
-  double yLoc = yDist / 2;
-  for (uint32_t i = 0; i < m_ySize; ++i)
-  {
-    double xLoc = xDist / 2;
-    for (uint32_t j = 0; j < m_xSize; ++j)
-    {
-      Ptr<Node> node = GetNode (i, j);
-      Ptr<NodeLocation> loc = node->GetObject<NodeLocation> ();
-      if (loc ==0)
-      {
-        loc = CreateObject<NodeLocation> ();
-        node->AggregateObject (loc);
-      }
-      Vector locVec (xLoc, yLoc, 0);
-      loc->SetLocation (locVec);
-
-      xLoc += xAdder;
-    }
-    yLoc += yAdder;
-  }
-}
-
-Ptr<Node> 
-PointToPointGridHelper::GetNode (uint32_t row, uint32_t col)
-{
-    return (m_nodes.at (row)).Get (col);
-}
-
-Ipv4Address
-PointToPointGridHelper::GetAddress (uint32_t row, uint32_t col)
-{
-  // Right now this just gets one of the addresses of the
-  // specified node.  The exact device can't be specified.
-  // If you picture the grid, the address returned is the 
-  // address of the left (row) device of all nodes, with 
-  // the exception of the left-most nodes in the grid; 
-  // in which case the right (row) device address is 
-  // returned
-  if (col == 0)
-  {
-    return (m_rowInterfaces.at (row)).GetAddress (0);
-  }
-  else
-  {
-    return (m_rowInterfaces.at (row)).GetAddress ((2*col)-1);
-  }
-}
-
-} // namespace ns3
--- a/src/contrib/net-anim/point-to-point-grid-helper.h	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,57 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: Josh Pelkey <jpelkey@gatech.edu>
- */
-
-#ifndef __POINT_TO_POINT_GRID_HELPER_H__
-#define __POINT_TO_POINT_GRID_HELPER_H__
-
-#include <vector>
-
-#include "internet-stack-helper.h"
-#include "point-to-point-helper.h"
-#include "ipv4-address-helper.h"
-#include "ipv4-interface-container.h"
-#include "net-device-container.h"
-
-namespace ns3 {
-  
-class PointToPointGridHelper 
-{
-  public: 
-    PointToPointGridHelper (uint32_t nRows, uint32_t nCols, PointToPointHelper pointToPoint);
-
-    Ptr<Node> GetNode (uint32_t row, uint32_t col);
-    Ipv4Address GetAddress (uint32_t row, uint32_t col);
-
-    void InstallStack (InternetStackHelper stack);
-    void AssignAddresses (Ipv4AddressHelper rowIp, Ipv4AddressHelper colIp);
-    void BoundingBox (double ulx, double uly, double lrx, double lry);
-
-  private:
-    uint32_t m_xSize;
-    uint32_t m_ySize;
-    std::vector<NetDeviceContainer> m_rowDevices;
-    std::vector<NetDeviceContainer> m_colDevices;
-    std::vector<Ipv4InterfaceContainer> m_rowInterfaces;
-    std::vector<Ipv4InterfaceContainer> m_colInterfaces;
-    std::vector<NodeContainer> m_nodes;
-
-};
-
-} // namespace ns3
-      
-#endif /* GRID_HELPER_H */
--- a/src/contrib/net-anim/test-dumbbell.cc	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,119 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: George F. Riley<riley@ece.gatech.edu>
- */
-
-#include <iostream>
-
-#include "ns3/core-module.h"
-#include "ns3/simulator-module.h"
-#include "ns3/node-module.h"
-#include "ns3/helper-module.h"
-#include "ns3/net-anim-module.h"
-
-using namespace ns3;
-
-int main (int argc, char *argv[])
-{
-  Config::SetDefault ("ns3::OnOffApplication::PacketSize", UintegerValue (512));
-  Config::SetDefault ("ns3::OnOffApplication::DataRate", StringValue ("500kb/s"));
-
-  uint32_t    nLeftLeaf = 5;
-  uint32_t    nRightLeaf = 5;
-  uint32_t    nLeaf = 0; // If non-zero, number of both left and right
-  uint16_t    port = 0;  // If non zero, port to bind to for anim connection
-  std::string animFile;  // Name of file for animation output
-
-  CommandLine cmd;
-  cmd.AddValue ("nLeftLeaf", "Number of left side leaf nodes", nLeftLeaf);
-  cmd.AddValue ("nRightLeaf","Number of right side leaf nodes", nRightLeaf);
-  cmd.AddValue ("nLeaf",     "Number of left and right side leaf nodes", nLeaf);
-  cmd.AddValue ("port",      "Port Number for Remote Animation", port);
-  cmd.AddValue ("animFile",  "File Name for Animation Output", animFile);
-
-  cmd.Parse (argc,argv);
-  if (nLeaf > 0)
-    {
-      nLeftLeaf = nLeaf;
-      nRightLeaf = nLeaf;
-    }
-  
-  // Create the point-to-point link helpers
-  PointToPointHelper pointToPointRouter;
-  pointToPointRouter.SetDeviceAttribute  ("DataRate", StringValue ("10Mbps"));
-  pointToPointRouter.SetChannelAttribute ("Delay", StringValue ("1ms"));
-  PointToPointHelper pointToPointLeaf;
-  pointToPointLeaf.SetDeviceAttribute    ("DataRate", StringValue ("10Mbps"));
-  pointToPointLeaf.SetChannelAttribute   ("Delay", StringValue ("1ms"));
-
-  PointToPointDumbbellHelper d(nLeftLeaf, pointToPointLeaf,
-                   nRightLeaf, pointToPointLeaf,
-                   pointToPointRouter);
-
-  // Install Stack
-  InternetStackHelper stack;
-  d.InstallStack (stack);
-
-  // Assign IP Addresses
-  d.AssignAddresses(Ipv4AddressHelper("10.1.1.0", "255.255.255.0"),
-                    Ipv4AddressHelper("10.2.1.0", "255.255.255.0"),
-                    Ipv4AddressHelper("10.3.1.0", "255.255.255.0"));
-  
-  // Install on/off app on all right side nodes
-  OnOffHelper clientHelper ("ns3::UdpSocketFactory", Address ());
-  clientHelper.SetAttribute 
-    ("OnTime", RandomVariableValue (UniformVariable (0, 1)));
-  clientHelper.SetAttribute 
-    ("OffTime", RandomVariableValue (UniformVariable (0, 1)));
-  ApplicationContainer clientApps;
-
-  for (uint32_t i = 0; i < d.RightCount(); ++i)
-    {
-      // Create an on/off app sending packets to the same leaf right side
-      AddressValue remoteAddress(InetSocketAddress(d.GetLeftAddress(i), 1000));
-      clientHelper.SetAttribute("Remote", remoteAddress);
-      clientApps.Add(clientHelper.Install(d.GetRight(i)));
-    }
-
-  clientApps.Start (Seconds (0.0));
-  clientApps.Stop (Seconds (10.0));
-
-  // Set the bounding box for animation
-  d.BoundingBox(1, 1, 10, 10);
-
-  // Create the animation object and configure for specified output
-  AnimationInterface anim;
-  if (port > 0)
-    {
-      anim.SetServerPort(port);
-    }
-  else if (!animFile.empty())
-    {
-      anim.SetOutputFile(animFile);
-    }
-  anim.StartAnimation();
-  
-  // Set up the acutal simulation
-  Ipv4GlobalRoutingHelper::PopulateRoutingTables ();
-
-  std::cout << "Running the simulation" << std::endl;
-  Simulator::Run ();
-  std::cout << "Destroying the simulation" << std::endl;
-  Simulator::Destroy ();
-  std::cout << "Stopping the animation" << std::endl;
-  anim.StopAnimation();
-  return 0;
-}
--- a/src/contrib/net-anim/test-grid.cc	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,109 +0,0 @@
-/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
-/*
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation;
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program; if not, write to the Free Software
- * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
- *
- * Author: Josh Pelkey <jpelkey@gatech.edu>
- */
-
-#include <iostream>
-
-#include "ns3/core-module.h"
-#include "ns3/simulator-module.h"
-#include "ns3/node-module.h"
-#include "ns3/helper-module.h"
-#include "ns3/net-anim-module.h"
-
-using namespace ns3;
-
-int main (int argc, char *argv[])
-{
-  Config::SetDefault ("ns3::OnOffApplication::PacketSize", UintegerValue (512));
-  Config::SetDefault ("ns3::OnOffApplication::DataRate", StringValue ("500kb/s"));
-
-  uint32_t xSize = 5;
-  uint32_t ySize = 5;
-  uint16_t port = 0;
-  std::string animFile;
-
-  CommandLine cmd;
-  cmd.AddValue ("xSize", "Number of rows of nodes", xSize);
-  cmd.AddValue ("ySize", "Number of columns of nodes", ySize);
-  cmd.AddValue ("port",  "Port Number for Remote Animation", port);
-  cmd.AddValue ("animFile",  "File Name for Animation Output", animFile);
-
-  cmd.Parse (argc,argv);
-  if (xSize < 1)
-    NS_FATAL_ERROR ("Need more nodes for grid.");
-  if (ySize < 1)
-    NS_FATAL_ERROR ("Need more nodes for grid.");
-  if (xSize < 2 && ySize < 2)
-    NS_FATAL_ERROR ("Need more nodes for grid.");
-  
-  PointToPointHelper pointToPoint;
-  pointToPoint.SetDeviceAttribute ("DataRate", StringValue ("5Mbps"));
-  pointToPoint.SetChannelAttribute ("Delay", StringValue ("2ms"));
-
-  // Create Grid
-  PointToPointGridHelper grid (xSize, ySize, pointToPoint);
-
-  // Install stack on Grid
-  InternetStackHelper stack;
-  grid.InstallStack (stack);
-
-  // Assign Addresses to Grid
-  grid.AssignAddresses (Ipv4AddressHelper("10.1.1.0", "255.255.255.0"),
-                        Ipv4AddressHelper("10.2.1.0", "255.255.255.0"));
-
-
-  OnOffHelper clientHelper ("ns3::UdpSocketFactory", Address ());
-  clientHelper.SetAttribute 
-    ("OnTime", RandomVariableValue (ConstantVariable (1)));
-  clientHelper.SetAttribute 
-    ("OffTime", RandomVariableValue (ConstantVariable (0)));
-  ApplicationContainer clientApps;
-
-  // Create an on/off app sending packets
-  AddressValue remoteAddress(InetSocketAddress(grid.GetAddress (xSize-1,ySize-1), 1000));
-  clientHelper.SetAttribute("Remote", remoteAddress);
-  clientApps.Add(clientHelper.Install(grid.GetNode (0,0)));
-
-  clientApps.Start (Seconds (0.0));
-  clientApps.Stop (Seconds (1.5));
-
-  // Set the bounding box for animation
-  grid.BoundingBox(1, 1, 10, 10);
-
-  // Create the animation object and configure for specified output
-  AnimationInterface anim;
-  if (port > 0)
-    {
-      anim.SetServerPort(port);
-    }
-  else if (!animFile.empty())
-    {
-      anim.SetOutputFile(animFile);
-    }
-  anim.StartAnimation();
-  
-  // Set up the actual simulation
-  Ipv4GlobalRoutingHelper::PopulateRoutingTables ();
-
-  std::cout << "Running the simulation" << std::endl;
-  Simulator::Run ();
-  std::cout << "Destroying the simulation" << std::endl;
-  Simulator::Destroy ();
-  std::cout << "Stopping the animation" << std::endl;
-  anim.StopAnimation();
-  return 0;
-}
--- a/src/contrib/net-anim/wscript	Tue Nov 24 14:00:39 2009 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,31 +0,0 @@
-## -*- Mode: python; py-indent-offset: 4; indent-tabs-mode: nil; coding: utf-8; -*-
-
-def configure(conf):
-    conf.check(header_name='sys/socket.h', define_name='HAVE_SYS_SOCKET_H')
-    conf.check(header_name='netinet/in.h', define_name='HAVE_NETINET_IN_H')
-    conf.write_config_header('ns3/net-anim-config.h', top=True)
-
-
-def build(bld):
-    obj = bld.create_ns3_module('net-anim')
-    obj.source = [
-        'point-to-point-dumbbell-helper.cc',
-        'point-to-point-grid-helper.cc',
-        'animation-interface.cc',
-        'node-location.cc'
-       ]
-
-    headers = bld.new_task_gen('ns3header')
-    headers.module = 'net-anim'
-    headers.source = [
-        'point-to-point-dumbbell-helper.h',
-        'point-to-point-grid-helper.h',
-        'animation-interface.h',
-        'node-location.h'
-       ]
-
-    obj = bld.create_ns3_program('test-dumbbell', ['net-anim', 'point-to-point', 'internet-stack'])
-    obj.source = 'test-dumbbell.cc'
-
-    obj = bld.create_ns3_program('test-grid', ['net-anim', 'point-to-point', 'internet-stack'])
-    obj.source = 'test-grid.cc'
--- a/src/contrib/wscript	Tue Nov 24 14:00:39 2009 +0100
+++ b/src/contrib/wscript	Tue Nov 24 10:16:58 2009 -0500
@@ -17,7 +17,6 @@
     conf.write_config_header('ns3/contrib-config.h', top=True)
 
     conf.sub_config('stats')
-    conf.sub_config('net-anim')
 
 
 def build(bld):
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/animation-interface.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,202 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: George F. Riley<riley@ece.gatech.edu>
+ */
+
+// Interface between ns3 and the network animator
+
+#include <stdio.h>
+#include <sstream>
+
+#include "ns3/net-anim-config.h"
+
+// Socket related includes
+#if defined(HAVE_SYS_SOCKET_H) && defined(HAVE_NETINET_IN_H)
+#include <sys/socket.h>
+#include <netinet/in.h>
+#else
+#include <fcntl.h>
+#endif
+
+// ns3 includes
+#include "ns3/animation-interface.h"
+#include "ns3/channel.h"
+#include "ns3/config.h"
+#include "ns3/node.h"
+#include "ns3/canvas-location.h"
+#include "ns3/packet.h"
+#include "ns3/simulator.h"
+
+using namespace std;
+
+NS_LOG_COMPONENT_DEFINE ("AnimationInterface");
+
+namespace ns3 {
+
+AnimationInterface::AnimationInterface ()
+  : m_fHandle (STDOUT_FILENO), m_model (0)
+{
+}
+
+AnimationInterface::~AnimationInterface ()
+{
+}
+
+bool AnimationInterface::SetOutputFile (const std::string& fn)
+{
+  FILE* f = fopen (fn.c_str (), "w");
+  if (!f)
+    {
+      return false; // Can't open
+    }
+  m_fHandle = fileno (f); // Set the file handle
+  return true;
+}
+
+bool AnimationInterface::SetServerPort (uint16_t port)
+{
+#if defined(HAVE_SYS_SOCKET_H) && defined(HAVE_NETINET_IN_H)
+  int s = socket (AF_INET, SOCK_STREAM, 0);
+  struct sockaddr_in addr;
+  addr.sin_family = AF_INET;
+  addr.sin_port = htons (port);
+  addr.sin_addr.s_addr = htonl (INADDR_ANY);
+  if (bind (s, (struct sockaddr*)&addr, sizeof (addr)) < 0)
+    {
+      NS_LOG_WARN ("Can't bind to port " << port << ", exiting.");
+      return false;
+    }
+  listen (s, 1);
+  NS_LOG_INFO ("Waiting for animator connection");
+  // Now wait for the animator to connect in
+  m_fHandle = accept (s, 0, 0);
+  NS_LOG_INFO ("Got animator connection from remote");
+  // set the linger socket option
+  int t = 1;
+  setsockopt (s, SOL_SOCKET, SO_LINGER, &t, sizeof(t));
+  return true;
+#endif
+  return false; // never reached unless the above is disabled
+                // which is done to support a platform like MinGW
+}
+
+void AnimationInterface::StartAnimation ()
+{
+  // Dump the topology
+  for (NodeList::Iterator i = NodeList::Begin (); i != NodeList::End (); ++i)
+    {
+      Ptr<Node> n = *i;
+      Ptr<CanvasLocation> loc = n->GetObject<CanvasLocation> ();
+      if (loc)
+        {
+          // Location exists, dump it
+          Vector v = loc->GetLocation ();
+          ostringstream oss;
+          oss << "0.0 N " << n->GetId () 
+               << " " << v.x << " " << v.y << endl;
+          WriteN (m_fHandle, oss.str ().c_str (), oss.str ().length ());
+        }
+    }
+  // Now dump the p2p links
+  for (NodeList::Iterator i = NodeList::Begin (); i != NodeList::End (); ++i)
+    {
+      Ptr<Node> n = *i;
+      uint32_t n1Id = n->GetId ();
+      uint32_t nDev = n->GetNDevices ();  // Number of devices
+      for (uint32_t i = 0; i < nDev; ++i)
+        {
+          Ptr<NetDevice> dev = n->GetDevice (i);
+          Ptr<Channel>   ch = dev->GetChannel ();
+          if (!ch) 
+            {
+              continue; // No channel, can't be p2p device
+            }
+          string channelType = ch->GetInstanceTypeId ().GetName ();
+          if (channelType == string ("ns3::PointToPointChannel"))
+            { // Since these are duplex links, we only need to dump
+              // if srcid < dstid
+              uint32_t nChDev = ch->GetNDevices ();
+              for (uint32_t j = 0; j < nChDev; ++j)
+                {
+                  Ptr<NetDevice> chDev = ch->GetDevice (j);
+                  uint32_t n2Id = chDev->GetNode ()->GetId ();
+                  if (n1Id < n2Id)
+                    { // ouptut the p2p link
+                      ostringstream oss;
+                      oss << "0.0 L "  << n1Id << " " << n2Id << endl;
+                      WriteN (m_fHandle, oss.str ().c_str (),
+                             oss.str ().length ());
+                    }
+                }
+            }
+          else
+            {
+              NS_FATAL_ERROR ("Net animation currently only supports point-to-point links.");
+            }
+        }
+    }
+  
+  // Connect the callback for packet tx events
+  Config::Connect ("/ChannelList/*/TxRxPointToPoint",
+                   MakeCallback (&AnimationInterface::DevTxTrace, this));
+}
+
+void AnimationInterface::StopAnimation ()
+{
+  if (m_fHandle > 0) 
+    {
+      close (m_fHandle);
+    }
+}
+
+
+// Private methods
+int AnimationInterface::WriteN (int h, const char* data, uint32_t count)
+{ // Write count bytes to h from data
+  uint32_t    nLeft   = count;
+  const char* p       = data;
+  uint32_t    written = 0;
+
+  while (nLeft)
+    {
+      int n = write (h, p, nLeft);
+      if (n <= 0) 
+        {
+          return written;
+        }
+      written += n;
+      nLeft -= n;
+      p += n;
+    }
+  return written;
+}
+  
+void AnimationInterface::DevTxTrace (std::string context, Ptr<const Packet> p,
+                                     Ptr<NetDevice> tx, Ptr<NetDevice> rx,
+                                     Time txTime, Time rxTime)
+{
+  Time now = Simulator::Now ();
+  ostringstream oss;
+  oss << now.GetSeconds() << " P "
+      << tx->GetNode ()->GetId () << " "
+      << rx->GetNode ()->GetId () << " "
+      << (now + txTime).GetSeconds () << " " // last bit tx time
+      << (now + rxTime - txTime).GetSeconds() << " "  // first bit rx time
+      << (now + rxTime).GetSeconds () << endl;         // last bit rx time
+  WriteN (m_fHandle, oss.str ().c_str (), oss.str ().length ());
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/animation-interface.h	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,112 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: George F. Riley<riley@ece.gatech.edu>
+ */
+
+// Interface between ns3 and the network animator
+
+#ifndef ANIMATION_INTERFACE__H
+#define ANIMATION_INTERFACE__H
+
+#include <string>
+
+#include "ns3/ptr.h"
+#include "ns3/net-device.h"
+#include "ns3/nstime.h"
+#include "ns3/log.h"
+#include "ns3/node-list.h"
+
+
+namespace ns3 {
+class NetModel;
+
+/**
+ * \brief Interface to network animator
+ *
+ * Provides functions that facilitate communications with an
+ * external or internal network animator.
+ */
+class AnimationInterface
+{
+public:
+/**
+ * @brief Construct the animator interface. No arguments needed.
+ */
+  AnimationInterface ();
+/**
+ * @brief Destructor for the animator interface.
+ */
+  ~AnimationInterface ();
+/**
+ * @brief Specify that animation commands are to be written
+ * to the specified output file.
+ *
+ * This call is used to write the animation information to a text
+ * file that can later be used as input to the network animator tool.
+ *
+ * @param fn The name of the output file.
+ * @returns true if successful open.
+ */
+  bool SetOutputFile (const std::string& fn);
+
+/**
+ * @brief Specify that animation commands are to be written to
+ * a socket.
+ *
+ * This call is used to set the ns3 process in server mode, waiting
+ * for a TCP connection from the animator.  This call will not
+ * return until the animator connects in, or if the bind to the
+ * specified port fails.
+ *
+ * @param port Port number to bind to.
+ * @returns true if connection created, false if bind failed.
+ */
+  bool SetServerPort (uint16_t port);
+
+/**
+ * @brief Writes the topology information and sets up the appropriate
+ *  animation packet tx callback
+ *
+ * Writes the topology information to the appropriate output, depending
+ * on prior calls to SetOutputFile, SetServerPort, or SetInternalAnimation.
+ * Then creates the callbacks needed for the animator to start processing
+ * packets.
+ *
+ */
+  void StartAnimation ();
+
+/**
+ * @brief Closes the interface to the animator.
+ *
+ */
+  void StopAnimation ();
+
+
+private:
+  // Packet tx animation callback
+  void DevTxTrace (std::string context, Ptr<const Packet> p,
+                 Ptr<NetDevice> tx, Ptr<NetDevice> rx,
+                 Time txTime, Time rxTime);
+  // Write specified amount of data to the specified handle
+  int  WriteN (int, const char*, uint32_t);
+private:
+  int       m_fHandle;  // File handle for output (-1 if none)
+  NetModel* m_model;    // If non nil, points to the internal network model
+                        // for the interlan animator
+};
+}
+#endif
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/canvas-location.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,58 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2009 Georgia Institute of Technology
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: George Riley<riley@ece.gatech.edu>
+ */
+
+#include "canvas-location.h"
+
+namespace ns3 {
+
+TypeId 
+CanvasLocation::GetTypeId (void)
+{
+  static TypeId tid = TypeId ("ns3::CanvasLocation")
+    .SetParent<Object> ()
+    .AddAttribute ("Location", "The current location on the canvas.",
+                   TypeId::ATTR_SET | TypeId::ATTR_GET,
+                   VectorValue (Vector (0.0, 0.0, 0.0)),
+                   MakeVectorAccessor (&CanvasLocation::SetLocation,
+                                        &CanvasLocation::GetLocation),
+                   MakeVectorChecker ())
+    ;
+  return tid;
+}
+
+CanvasLocation::CanvasLocation ()
+{}
+
+CanvasLocation::~CanvasLocation ()
+{}
+
+Vector 
+CanvasLocation::GetLocation (void) const
+{
+  return m_location;
+}
+
+void 
+CanvasLocation::SetLocation (const Vector &location)
+{
+  m_location = location;
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/canvas-location.h	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,61 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2009 Georgia Institute of Technology
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: George Riley<riley@ece.gatech.edu>
+ */
+#ifndef CANVAS_LOCATION_H
+#define CANVAS_LOCATION_H
+
+#include "ns3/object.h"
+#include "ns3/traced-callback.h"
+#include "ns3/vector.h"
+
+namespace ns3 {
+
+/**
+ * \brief Keep track of the current location of an object
+ *
+ * This can be used anytime a logical node location is needed
+ * (as opposed to a physical location used by the wireless PHY
+ * layer to calculate path loss).  One potential use of 
+ * this is by the animator to determine where to position the
+ * node icon on the animation display.  Location units are 
+ * arbitrary and dimensionless.  In the case of use by the
+ * animator they dimensions are in pixels.
+ */
+class CanvasLocation : public Object
+{
+public:
+  static TypeId GetTypeId (void);
+  CanvasLocation ();
+  virtual ~CanvasLocation ();
+
+  /**
+   * \returns the current location
+   */
+  Vector GetLocation (void) const;
+  /**
+   * \param location the location to set.
+   */
+  void SetLocation (const Vector &location);
+private:
+  Vector m_location;
+};
+
+}; // namespace ns3
+
+#endif /* CANVAS_LOCATION_H */
--- a/src/helper/csma-helper.cc	Tue Nov 24 14:00:39 2009 +0100
+++ b/src/helper/csma-helper.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -269,27 +269,6 @@
 }
 
 void 
-CsmaHelper::InstallStar (Ptr<Node> hub, NodeContainer spokes, 
-                         NetDeviceContainer& hubDevices, NetDeviceContainer& spokeDevices)
-{
-  for (uint32_t i = 0; i < spokes.GetN (); ++i)
-    {
-      NodeContainer nodes (hub, spokes.Get (i));
-      NetDeviceContainer nd = Install (nodes);
-      hubDevices.Add (nd.Get (0));
-      spokeDevices.Add (nd.Get (1));
-    }
-}
-
-void 
-CsmaHelper::InstallStar (std::string hubName, NodeContainer spokes, 
-                         NetDeviceContainer& hubDevices, NetDeviceContainer& spokeDevices)
-{
-  Ptr<Node> hub = Names::Find<Node> (hubName);
-  InstallStar (hub, spokes, hubDevices, spokeDevices);
-}
-
-void 
 CsmaHelper::SniffEvent (Ptr<PcapWriter> writer, Ptr<const Packet> packet)
 {
   writer->WritePacket (packet);
--- a/src/helper/csma-helper.h	Tue Nov 24 14:00:39 2009 +0100
+++ b/src/helper/csma-helper.h	Tue Nov 24 10:16:58 2009 -0500
@@ -285,72 +285,6 @@
    */
   NetDeviceContainer Install (const NodeContainer &c, std::string channelName) const;
 
-  /**
-   * \brief Make a star network topology.
-   *
-   * Given a pointer to a node that  will become the hub of the star, and a 
-   * NodeContainer containing pointers to the nodes that will become the 
-   * spokes; we construct CSMA net devices on the hub (corresponding to the 
-   * spokes) and store them in the hubDevices NetDeviceContainer.  We add a 
-   * net device to each spoke node and store them in the spokeDevices 
-   * NetDeviceContainer.  A CSMA is created for each spoke.
-   *
-   * Usually when one thinks of a star network, one thinks of point-to-point
-   * links.  We're just using a single pair of devices on a multi-point-to-point
-   * network "drops" as the link.  You are free to add any number of other 
-   * devices on the link if you want.
-   *
-   * The ordering of the devices in the hubDevices container is according to
-   * the order of the spokes container -- that is, hubDevices[0] will be the
-   * net device used on the hub that talks to spokes[0].  the container entry
-   * spokeDevices[0] will have the device that hubDevices[0] talks to -- those
-   * two devices are the ones that connect hub to spokes[0].
-   *
-   * \param hub The central node of the star network
-   * \param spokes A NodeContainer of the nodes that will be the spoke (leaf)
-   *               nodes
-   * \param hubDevices A NetDeviceContainer that will be filled with pointers
-   *                   to the point-to-point net devices created on the hub.
-   * \param spokeDevices A NetDeviceContainer that will be filled with pointers
-   *                    to the point-to-point net devices created on each of 
-   *                    the spokes.
-   */
-  void InstallStar (Ptr<Node> hub, NodeContainer spokes, 
-                    NetDeviceContainer& hubDevices, NetDeviceContainer& spokeDevices);
-
-  /**
-   * \brief Make a star network topology.
-   *
-   * Given a pointer to a node that  will become the hub of the star, and a 
-   * NodeContainer containing pointers to the nodes that will become the 
-   * spokes; we construct CSMA net devices on the hub (corresponding to the 
-   * spokes) and store them in the hubDevices NetDeviceContainer.  We add a 
-   * net device to each spoke node and store them in the spokeDevices 
-   * NetDeviceContainer.  A CSMA is created for each spoke.
-   *
-   * Usually when one thinks of a star network, one thinks of point-to-point
-   * links.  We're just using a single pair of devices on a multi-point-to-point
-   * network "drops" as the link.  You are free to add any number of other 
-   * devices on the link if you want.
-   *
-   * The ordering of the devices in the hubDevices container is according to
-   * the order of the spokes container -- that is, hubDevices[0] will be the
-   * net device used on the hub that talks to spokes[0].  the container entry
-   * spokeDevices[0] will have the device that hubDevices[0] talks to -- those
-   * two devices are the ones that connect hub to spokes[0].
-   *
-   * \param hubName The name of the central node of the star network
-   * \param spokes A NodeContainer of the nodes that will be the spoke (leaf)
-   *               nodes
-   * \param hubDevices A NetDeviceContainer that will be filled with pointers
-   *                   to the point-to-point net devices created on the hub.
-   * \param spokeDevices A NetDeviceContainer that will be filled with pointers
-   *                     to the point-to-point net devices created on each of 
-   *                     the spokes.
-   */
-  void InstallStar (std::string hubName, NodeContainer spokes, 
-                    NetDeviceContainer& hubDevices, NetDeviceContainer& spokeDevices);
-
 private:
   /*
    * \internal
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/csma-star-helper.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,110 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+#include <iostream>
+#include <sstream>
+
+// ns3 includes
+#include "ns3/animation-interface.h"
+#include "ns3/csma-star-helper.h"
+
+#include "ns3/node-list.h"
+#include "ns3/point-to-point-net-device.h"
+#include "ns3/vector.h"
+
+NS_LOG_COMPONENT_DEFINE("CsmaStarHelper");
+
+namespace ns3 {
+  
+CsmaStarHelper::CsmaStarHelper (uint32_t numSpokes,
+                                CsmaHelper csmaHelper)
+{
+  m_hub.Create (1);
+  m_spokes.Create (numSpokes);
+
+  for (uint32_t i = 0; i < m_spokes.GetN (); ++i)
+    {
+      NodeContainer nodes (m_hub.Get (0), m_spokes.Get (i));
+      NetDeviceContainer nd = csmaHelper.Install (nodes);
+      m_hubDevices.Add (nd.Get (0));
+      m_spokeDevices.Add (nd.Get (1));
+    }
+}
+
+CsmaStarHelper::~CsmaStarHelper ()
+{}
+
+Ptr<Node> 
+CsmaStarHelper::GetHub () const
+{
+  return m_hub.Get (0);
+}
+
+Ptr<Node> 
+CsmaStarHelper::GetSpoke (uint32_t i) const
+{
+  return m_spokes.Get (i);
+}
+
+NetDeviceContainer
+CsmaStarHelper::GetHubDevices () const
+{
+  return m_spokeDevices;
+}
+
+NetDeviceContainer
+CsmaStarHelper::GetSpokeDevices () const
+{
+  return m_spokeDevices;
+}
+
+Ipv4Address 
+CsmaStarHelper::GetHubIpv4Address (uint32_t i) const
+{
+  return m_hubInterfaces.GetAddress (i);
+}
+
+Ipv4Address 
+CsmaStarHelper::GetSpokeIpv4Address (uint32_t i) const
+{
+  return m_spokeInterfaces.GetAddress (i);
+}
+
+uint32_t  
+CsmaStarHelper::SpokeCount () const
+{
+  return m_spokes.GetN ();
+}
+
+void 
+CsmaStarHelper::InstallStack (InternetStackHelper stack)
+{
+  stack.Install (m_hub);
+  stack.Install (m_spokes);
+}
+
+void 
+CsmaStarHelper::AssignIpv4Addresses (Ipv4AddressHelper address)
+{
+  for (uint32_t i = 0; i < m_spokes.GetN (); ++i)
+    {
+      m_hubInterfaces.Add (address.Assign (m_hubDevices.Get (i)));
+      m_spokeInterfaces.Add (address.Assign (m_spokeDevices.Get (i)));
+      address.NewNetwork ();
+    }
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/csma-star-helper.h	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,59 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+// Define an object to create a dumbbell topology.
+
+#ifndef CSMA_STAR_HELPER_H
+#define CSMA_STAR_HELPER_H
+
+#include <string>
+
+#include "csma-helper.h"
+#include "ipv4-address-helper.h"
+#include "internet-stack-helper.h"
+#include "ipv4-interface-container.h"
+
+namespace ns3 {
+  
+class CsmaStarHelper
+{
+public:
+  CsmaStarHelper (uint32_t numSpokes, 
+                  CsmaHelper csmaHelper);
+  ~CsmaStarHelper ();
+public:
+  Ptr<Node> GetHub () const;
+  Ptr<Node> GetSpoke (uint32_t) const;
+  NetDeviceContainer GetHubDevices () const;
+  NetDeviceContainer GetSpokeDevices () const;
+  Ipv4Address GetHubIpv4Address (uint32_t) const;
+  Ipv4Address GetSpokeIpv4Address (uint32_t) const;
+  uint32_t SpokeCount () const;
+  void InstallStack (InternetStackHelper stack);
+  void AssignIpv4Addresses (Ipv4AddressHelper address);
+
+private:
+  NodeContainer m_hub;
+  NetDeviceContainer m_hubDevices;
+  NodeContainer m_spokes;
+  NetDeviceContainer m_spokeDevices;
+  Ipv4InterfaceContainer m_hubInterfaces;
+  Ipv4InterfaceContainer m_spokeInterfaces;
+};
+}
+#endif
+
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/point-to-point-dumbbell-helper.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,267 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: George F. Riley<riley@ece.gatech.edu>
+ */
+
+// Implement an object to create a dumbbell topology.
+
+#include <iostream>
+#include <sstream>
+
+// ns3 includes
+#include "ns3/animation-interface.h"
+#include "ns3/point-to-point-dumbbell-helper.h"
+#include "ns3/canvas-location.h"
+
+#include "ns3/node-list.h"
+#include "ns3/point-to-point-net-device.h"
+#include "ns3/vector.h"
+
+NS_LOG_COMPONENT_DEFINE("PointToPointDumbbellHelper");
+
+namespace ns3 {
+  
+PointToPointDumbbellHelper::PointToPointDumbbellHelper (uint32_t nLeftLeaf,
+                   PointToPointHelper leftHelper,
+                   uint32_t nRightLeaf,
+                   PointToPointHelper rightHelper,
+                   PointToPointHelper bottleneckHelper)
+{
+  // Create the bottleneck routers
+  m_routers.Create (2);
+  // Create the leaf nodes
+  m_leftLeaf.Create (nLeftLeaf);
+  m_rightLeaf.Create (nRightLeaf);
+
+  // Add the link connecting routers
+  m_routerDevices = bottleneckHelper.Install (m_routers);
+  // Add the left side links
+  for (uint32_t i = 0; i < nLeftLeaf; ++i)
+    {
+      NetDeviceContainer c = leftHelper.Install (m_routers.Get (0),
+                                                m_leftLeaf.Get (i));
+      m_leftRouterDevices.Add (c.Get (0));
+      m_leftLeafDevices.Add (c.Get(1));
+    }
+  // Add the right side links
+  for (uint32_t i = 0; i < nRightLeaf; ++i)
+    {
+      NetDeviceContainer c = rightHelper.Install (m_routers.Get (1),
+                                                m_rightLeaf.Get (i));
+      m_rightRouterDevices.Add (c.Get (0));
+      m_rightLeafDevices.Add (c.Get (1));
+    }
+}
+
+PointToPointDumbbellHelper::~PointToPointDumbbellHelper ()
+{}
+
+Ptr<Node> PointToPointDumbbellHelper::GetLeft () const
+{ // Get the left side bottleneck router
+  return m_routers.Get (0);
+}
+
+Ptr<Node> PointToPointDumbbellHelper::GetLeft (uint32_t i) const
+{ // Get the i'th left side leaf
+  return m_leftLeaf.Get (i);
+}
+
+Ptr<Node> PointToPointDumbbellHelper::GetRight () const
+{ // Get the right side bottleneck router
+  return m_routers.Get (1);
+}
+
+Ptr<Node> PointToPointDumbbellHelper::GetRight (uint32_t i) const
+{ // Get the i'th right side leaf
+  return m_rightLeaf.Get (i);
+}
+
+Ipv4Address PointToPointDumbbellHelper::GetLeftIpv4Address (uint32_t i) const
+{
+  return m_leftLeafInterfaces.GetAddress (i);
+}
+
+Ipv4Address PointToPointDumbbellHelper::GetRightIpv4Address (uint32_t i) const
+{
+  return m_rightLeafInterfaces.GetAddress (i);
+}
+
+uint32_t  PointToPointDumbbellHelper::LeftCount () const
+{ // Number of left side nodes
+  return m_leftLeaf.GetN ();
+}
+
+uint32_t  PointToPointDumbbellHelper::RightCount () const
+{ // Number of right side nodes
+  return m_rightLeaf.GetN ();
+}
+
+void PointToPointDumbbellHelper::InstallStack (InternetStackHelper stack)
+{
+  stack.Install (m_routers);
+  stack.Install (m_leftLeaf);
+  stack.Install (m_rightLeaf);
+}
+
+void PointToPointDumbbellHelper::AssignIpv4Addresses (Ipv4AddressHelper leftIp,
+                               Ipv4AddressHelper rightIp,
+                               Ipv4AddressHelper routerIp)
+{
+  // Assign the router network
+  m_routerInterfaces = routerIp.Assign (m_routerDevices);
+  // Assign to left side 
+  for (uint32_t i = 0; i < LeftCount (); ++i)
+    {
+      NetDeviceContainer ndc;
+      ndc.Add (m_leftLeafDevices.Get (i));
+      ndc.Add (m_leftRouterDevices.Get (i));
+      Ipv4InterfaceContainer ifc = leftIp.Assign(ndc);
+      m_leftLeafInterfaces.Add (ifc.Get (0));
+      m_leftRouterInterfaces.Add (ifc.Get (1));
+      leftIp.NewNetwork ();
+    }
+  // Assign to right side
+  for (uint32_t i = 0; i < RightCount (); ++i)
+    {
+      NetDeviceContainer ndc;
+      ndc.Add (m_rightLeafDevices.Get (i));
+      ndc.Add (m_rightRouterDevices.Get (i));
+      Ipv4InterfaceContainer ifc = rightIp.Assign (ndc);
+      m_rightLeafInterfaces.Add (ifc.Get (0));
+      m_rightRouterInterfaces.Add (ifc.Get (1));
+      rightIp.NewNetwork ();
+    }
+}
+
+
+void PointToPointDumbbellHelper::BoundingBox (double ulx, double uly, // Upper left x/y
+                           double lrx, double lry) // Lower right y
+{
+  double xDist;
+  double yDist;
+  if (lrx > ulx)
+    {
+      xDist = lrx - ulx;
+    }
+  else
+    {
+      xDist = ulx - lrx;
+    }
+  if (lry > uly)
+    {
+      yDist = lry - uly;
+    }
+  else
+    {
+      yDist = uly - lry;
+    }
+
+  double xAdder = xDist / 3.0;
+  double  thetaL = M_PI / (LeftCount () + 1.0);
+  double  thetaR = M_PI / (RightCount () + 1.0);
+
+  // Place the left router
+  Ptr<Node> lr = GetLeft ();
+  Ptr<CanvasLocation> loc = lr->GetObject<CanvasLocation> ();
+  if (loc == 0)
+    {
+      loc = CreateObject<CanvasLocation> ();
+      lr->AggregateObject (loc);
+    }
+  Vector lrl (ulx + xAdder, uly + yDist/2.0, 0);
+  loc->SetLocation (lrl);
+  
+  // Place the right router
+  Ptr<Node> rr = GetRight ();
+  loc = rr->GetObject<CanvasLocation> ();
+  if (loc == 0)
+    {
+      loc = CreateObject<CanvasLocation> ();
+      rr->AggregateObject (loc);
+    }
+  Vector rrl (ulx + xAdder * 2, uly + yDist/2.0, 0); // Right router location
+  loc->SetLocation (rrl);
+
+  // Place the left leaf nodes
+  double theta = -M_PI_2 + thetaL;
+  for (uint32_t l = 0; l < LeftCount (); ++l)
+    {
+      // Make them in a circular pattern to make all line lengths the same
+      // Special case when theta = 0, to be sure we get a straight line
+      if ((LeftCount () % 2) == 1)
+        { // Count is odd, see if we are in middle
+          if (l == (LeftCount () / 2))
+            {
+              theta = 0.0;
+            }
+        }
+      Ptr<Node> ln = GetLeft (l);
+      loc = ln->GetObject<CanvasLocation> ();
+      if (loc == 0)
+        {
+          loc = CreateObject<CanvasLocation> ();
+          ln->AggregateObject (loc);
+        }
+      Vector lnl (lrl.x - cos (theta) * xAdder,
+                   lrl.y + sin (theta) * xAdder, 0);  // Left Node Location
+      // Insure did not exceed bounding box
+      if (lnl.y < uly) 
+        {
+          lnl.y = uly; // Set to upper right y
+        }
+      if (lnl.y > lry) 
+        {
+          lnl.y = lry; // Set to lower right y
+        }
+      loc->SetLocation (lnl);
+      theta += thetaL;
+    }
+  // Place the right nodes
+  theta = -M_PI_2 + thetaR;
+  for (uint32_t r = 0; r < RightCount (); ++r)
+    {
+      // Special case when theta = 0, to be sure we get a straight line
+      if ((RightCount () % 2) == 1)
+        { // Count is odd, see if we are in middle
+          if (r == (RightCount () / 2))
+            {
+              theta = 0.0;
+            }
+        }
+      Ptr<Node> rn = GetRight (r);
+      loc = rn->GetObject<CanvasLocation> ();
+      if (loc == 0)
+        {
+          loc = CreateObject<CanvasLocation> ();
+          rn->AggregateObject (loc);
+        }
+      Vector rnl (rrl.x + cos (theta) * xAdder, // Right node location
+                   rrl.y + sin (theta) * xAdder, 0);
+      // Insure did not exceed bounding box
+      if (rnl.y < uly) 
+        {
+          rnl.y = uly; // Set to upper right y
+        }
+      if (rnl.y > lry) 
+        {
+          rnl.y = lry; // Set to lower right y
+        }
+      loc->SetLocation (rnl);
+      theta += thetaR;
+    }
+}
+  
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/point-to-point-dumbbell-helper.h	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,78 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: George F. Riley<riley@ece.gatech.edu>
+ */
+
+// Define an object to create a dumbbell topology.
+
+#ifndef POINT_TO_POINT_DUMBBELL_HELPER_H
+#define POINT_TO_POINT_DUMBBELL_HELPER_H
+
+#include <string>
+
+#include "point-to-point-helper.h"
+#include "ipv4-address-helper.h"
+#include "internet-stack-helper.h"
+#include "ipv4-interface-container.h"
+
+namespace ns3 {
+  
+class PointToPointDumbbellHelper
+{
+public:
+  PointToPointDumbbellHelper (uint32_t nLeftLeaf,  // Number of left size leaf nodes
+           PointToPointHelper leftHelper,
+           uint32_t nRightLeaf, // Number of right side leaf nodes
+           PointToPointHelper rightHelper,
+           PointToPointHelper bottleneckHelper);
+  ~PointToPointDumbbellHelper ();
+public:
+  Ptr<Node> GetLeft ()           const; // Get the left side bottleneck router
+  Ptr<Node> GetLeft (uint32_t)   const; // Get the i'th left side leaf
+  Ptr<Node> GetRight ()          const; // Get the right side bottleneck router
+  Ptr<Node> GetRight (uint32_t)  const; // Get the i'th right side leaf
+  Ipv4Address GetLeftIpv4Address (uint32_t)  const; // Get left leaf address
+  Ipv4Address GetRightIpv4Address (uint32_t) const; // Get right leaf address
+  uint32_t  LeftCount ()         const; // Number of left side nodes
+  uint32_t  RightCount ()        const; // Number of right side nodes
+  void      InstallStack (InternetStackHelper stack);
+  void      AssignIpv4Addresses (Ipv4AddressHelper leftIp,
+                            Ipv4AddressHelper rightIp,
+                            Ipv4AddressHelper routerIp);
+  // Add locations in the specified bounding box
+  // Arguments are uppler left x, upper left y, lower right x, lower right y
+  void      BoundingBox (double, double, double, double);
+  
+private:
+  NodeContainer          m_leftLeaf;
+  NetDeviceContainer     m_leftLeafDevices;
+  NodeContainer          m_rightLeaf;
+  NetDeviceContainer     m_rightLeafDevices;
+  NodeContainer          m_routers;
+  NetDeviceContainer     m_routerDevices; // just two connecting the routers
+  // Device containers for the router devices connecting to the leaf devices
+  NetDeviceContainer     m_leftRouterDevices;
+  NetDeviceContainer     m_rightRouterDevices;
+  Ipv4InterfaceContainer m_leftLeafInterfaces;
+  Ipv4InterfaceContainer m_leftRouterInterfaces;
+  Ipv4InterfaceContainer m_rightLeafInterfaces;
+  Ipv4InterfaceContainer m_rightRouterInterfaces;
+  Ipv4InterfaceContainer m_routerInterfaces;
+};
+}
+#endif
+
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/point-to-point-grid-helper.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,218 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: Josh Pelkey <jpelkey@gatech.edu>
+ */
+
+#include "ns3/point-to-point-grid-helper.h"
+#include "ns3/animation-interface.h"
+#include "ns3/internet-stack-helper.h"
+#include "ns3/point-to-point-helper.h"
+#include "ns3/canvas-location.h"
+#include "ns3/string.h"
+#include "ns3/vector.h"
+#include "ns3/log.h"
+
+NS_LOG_COMPONENT_DEFINE("PointToPointGridHelper");
+
+namespace ns3 {
+  
+PointToPointGridHelper::PointToPointGridHelper (uint32_t nRows, 
+                                                uint32_t nCols, 
+                                                PointToPointHelper pointToPoint)
+  : m_xSize (nCols), m_ySize (nRows)
+{
+  // Bounds check
+  if (m_xSize < 1 || m_ySize < 1 || (m_xSize < 2 && m_ySize < 2))
+    {
+      NS_FATAL_ERROR ("Need more nodes for grid.");
+    }
+
+  InternetStackHelper stack;
+
+  for (uint32_t y = 0; y < nRows; ++y)
+  {
+    NodeContainer rowNodes;
+    NetDeviceContainer rowDevices;
+    NetDeviceContainer colDevices;
+
+    for (uint32_t x = 0; x < nCols; ++x)
+    {
+      rowNodes.Create (1);
+
+      // install p2p links across the row
+      if (x > 0)
+      {
+        rowDevices.Add (pointToPoint.
+            Install (rowNodes.Get (x-1), rowNodes.Get (x)));
+      }
+
+      // install vertical p2p links
+      if (y > 0)
+      {
+        colDevices.Add(pointToPoint.
+                      Install ((m_nodes.at (y-1)).Get (x), rowNodes.Get (x)));
+      }
+    }
+
+    m_nodes.push_back (rowNodes);
+    m_rowDevices.push_back (rowDevices);
+
+    if (y > 0)
+      m_colDevices.push_back (colDevices);
+  }
+}
+
+PointToPointGridHelper::~PointToPointGridHelper ()
+{}
+
+void
+PointToPointGridHelper::InstallStack (InternetStackHelper stack)
+{
+  for (uint32_t i = 0; i < m_nodes.size (); ++i)
+    {
+      NodeContainer rowNodes = m_nodes[i];
+      for (uint32_t j = 0; j < rowNodes.GetN (); ++j)
+        {
+          stack.Install (rowNodes.Get (j));
+        }
+    }
+}
+
+void
+PointToPointGridHelper::AssignIpv4Addresses (Ipv4AddressHelper rowIp, Ipv4AddressHelper colIp)
+{
+  // Assign addresses to all row devices in the grid.
+  // These devices are stored in a vector.  Each row 
+  // of the grid has all the row devices in one entry 
+  // of the vector.  These entries come in pairs.
+  for (uint32_t i = 0; i < m_rowDevices.size (); ++i)
+    {
+      Ipv4InterfaceContainer rowInterfaces; 
+      NetDeviceContainer rowContainer = m_rowDevices[i];
+      for (uint32_t j = 0; j < rowContainer.GetN (); j+=2)
+        {
+          rowInterfaces.Add (rowIp.Assign (rowContainer.Get (j))); 
+          rowInterfaces.Add (rowIp.Assign (rowContainer.Get (j+1)));
+          rowIp.NewNetwork ();
+        }
+      m_rowInterfaces.push_back (rowInterfaces);
+    }
+
+  // Assign addresses to all col devices in the grid.
+  // These devices are stored in a vector.  Each col 
+  // of the grid has all the col devices in one entry 
+  // of the vector.  These entries come in pairs.
+  for (uint32_t i = 0; i < m_colDevices.size (); ++i)
+    {
+      Ipv4InterfaceContainer colInterfaces; 
+      NetDeviceContainer colContainer = m_colDevices[i];
+      for (uint32_t j = 0; j < colContainer.GetN (); j+=2)
+        {
+          colInterfaces.Add (colIp.Assign (colContainer.Get (j))); 
+          colInterfaces.Add (colIp.Assign (colContainer.Get (j+1)));
+          colIp.NewNetwork ();
+        }
+      m_colInterfaces.push_back (colInterfaces);
+    }
+}
+
+void
+PointToPointGridHelper::BoundingBox (double ulx, double uly,
+                         double lrx, double lry)
+{
+  double xDist; 
+  double yDist; 
+  if (lrx > ulx)
+    {
+      xDist = lrx - ulx;
+    }
+  else
+    {
+      xDist = ulx - lrx;
+    }
+  if (lry > uly)
+    {
+      yDist = lry - uly;
+    }
+  else
+    {
+      yDist = uly - lry;
+    }
+  double xAdder = xDist / m_xSize;
+  double yAdder = yDist / m_ySize;
+  double yLoc = yDist / 2;
+  for (uint32_t i = 0; i < m_ySize; ++i)
+  {
+    double xLoc = xDist / 2;
+    for (uint32_t j = 0; j < m_xSize; ++j)
+    {
+      Ptr<Node> node = GetNode (i, j);
+      Ptr<CanvasLocation> loc = node->GetObject<CanvasLocation> ();
+      if (loc ==0)
+      {
+        loc = CreateObject<CanvasLocation> ();
+        node->AggregateObject (loc);
+      }
+      Vector locVec (xLoc, yLoc, 0);
+      loc->SetLocation (locVec);
+
+      xLoc += xAdder;
+    }
+    yLoc += yAdder;
+  }
+}
+
+Ptr<Node> 
+PointToPointGridHelper::GetNode (uint32_t row, uint32_t col)
+{
+  if (row < 0 || col < 0 || 
+      row > m_nodes.size () - 1 || 
+      col > m_nodes.at (row).GetN () - 1) 
+    {
+       NS_FATAL_ERROR ("Index out of bounds in PointToPointGridHelper::GetNode.");
+    }
+
+  return (m_nodes.at (row)).Get (col);
+}
+
+Ipv4Address
+PointToPointGridHelper::GetIpv4Address (uint32_t row, uint32_t col)
+{
+  if (row < 0 || col < 0 || 
+      row > m_nodes.size () - 1 || 
+      col > m_nodes.at (row).GetN () - 1) 
+    {
+       NS_FATAL_ERROR ("Index out of bounds in PointToPointGridHelper::GetIpv4Address.");
+    }
+
+  // Right now this just gets one of the addresses of the
+  // specified node.  The exact device can't be specified.
+  // If you picture the grid, the address returned is the 
+  // address of the left (row) device of all nodes, with 
+  // the exception of the left-most nodes in the grid; 
+  // in which case the right (row) device address is 
+  // returned
+  if (col == 0)
+  {
+    return (m_rowInterfaces.at (row)).GetAddress (0);
+  }
+  else
+  {
+    return (m_rowInterfaces.at (row)).GetAddress ((2*col)-1);
+  }
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/point-to-point-grid-helper.h	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,58 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ * Author: Josh Pelkey <jpelkey@gatech.edu>
+ */
+
+#ifndef POINT_TO_POINT_GRID_HELPER_H
+#define POINT_TO_POINT_GRID_HELPER_H
+
+#include <vector>
+
+#include "internet-stack-helper.h"
+#include "point-to-point-helper.h"
+#include "ipv4-address-helper.h"
+#include "ipv4-interface-container.h"
+#include "net-device-container.h"
+
+namespace ns3 {
+  
+class PointToPointGridHelper 
+{
+  public: 
+    PointToPointGridHelper (uint32_t nRows, uint32_t nCols, PointToPointHelper pointToPoint);
+    ~PointToPointGridHelper ();
+
+    Ptr<Node> GetNode (uint32_t row, uint32_t col);
+    Ipv4Address GetIpv4Address (uint32_t row, uint32_t col);
+
+    void InstallStack (InternetStackHelper stack);
+    void AssignIpv4Addresses (Ipv4AddressHelper rowIp, Ipv4AddressHelper colIp);
+    void BoundingBox (double ulx, double uly, double lrx, double lry);
+
+  private:
+    uint32_t m_xSize;
+    uint32_t m_ySize;
+    std::vector<NetDeviceContainer> m_rowDevices;
+    std::vector<NetDeviceContainer> m_colDevices;
+    std::vector<Ipv4InterfaceContainer> m_rowInterfaces;
+    std::vector<Ipv4InterfaceContainer> m_colInterfaces;
+    std::vector<NodeContainer> m_nodes;
+
+};
+
+} // namespace ns3
+      
+#endif /* POINT_TO_POINT_GRID_HELPER_H */
--- a/src/helper/point-to-point-helper.cc	Tue Nov 24 14:00:39 2009 +0100
+++ b/src/helper/point-to-point-helper.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -233,26 +233,6 @@
 }
 
 void 
-PointToPointHelper::InstallStar (Ptr<Node> hub, NodeContainer spokes, 
-                                 NetDeviceContainer& hubDevices, NetDeviceContainer& spokeDevices)
-{
-  for (uint32_t i = 0; i < spokes.GetN (); ++i)
-    {
-      NetDeviceContainer nd = Install (hub, spokes.Get (i));
-      hubDevices.Add (nd.Get (0));
-      spokeDevices.Add (nd.Get (1));
-    }
-}
-
-void 
-PointToPointHelper::InstallStar (std::string hubName, NodeContainer spokes, 
-                                 NetDeviceContainer& hubDevices, NetDeviceContainer& spokeDevices)
-{
-  Ptr<Node> hub = Names::Find<Node> (hubName);
-  InstallStar (hub, spokes, hubDevices, spokeDevices);
-}
-
-void 
 PointToPointHelper::SniffEvent (Ptr<PcapWriter> writer, Ptr<const Packet> packet)
 {
   writer->WritePacket (packet);
--- a/src/helper/point-to-point-helper.h	Tue Nov 24 14:00:39 2009 +0100
+++ b/src/helper/point-to-point-helper.h	Tue Nov 24 10:16:58 2009 -0500
@@ -240,62 +240,6 @@
    */
   NetDeviceContainer Install (std::string aNode, std::string bNode);
 
-  /**
-   * \brief Make a star network topology.
-   *
-   * Given a pointer to a node that  will become the hub of the star, and a 
-   * NodeContainer containing pointers to the nodes that will become the 
-   * spokes; we construct point to point net devices on the hub (corresponding 
-   * to the spokes) and store them in the hubDevices NetDeviceContainer.  We 
-   * add a net device to each spoke node and store them in the spokeDevices 
-   * NetDeviceContainer.  A point-to-point channel is created for each spoke.
-   *
-   * The ordering of the devices in the hubDevices container is according to
-   * the order of the spokes container -- that is, hubDevices[0] will be the
-   * net device used on the hub that talks to spokes[0].  the container entry
-   * spokeDevices[0] will have the device that hubDevices[0] talks to -- those
-   * two devices are the ones that connect hub to spokes[0].
-   *
-   * \param hub The central node of the star network
-   * \param spokes A NodeContainer of the nodes that will be the spoke (leaf)
-   *               nodes
-   * \param hubDevices A NetDeviceContainer that will be filled with pointers
-   *                   to the point-to-point net devices created on the hub.
-   * \param spokeDevices A NetDeviceContainer that will be filled with pointers
-   *                    to the point-to-point net devices created on each of 
-   *                    the spokes.
-   */
-  void InstallStar (Ptr<Node> hub, NodeContainer spokes, 
-                    NetDeviceContainer& hubDevices, NetDeviceContainer& spokeDevices);
-
-  /**
-   * \brief Make a star network topology.
-   *
-   * Given a pointer to a node that  will become the hub of the star, and a 
-   * NodeContainer containing pointers to the nodes that will become the 
-   * spokes; we construct point to point net devices on the hub (corresponding 
-   * to the spokes) and store them in the hubDevices NetDeviceContainer.  We 
-   * add a net device to each spoke node and store them in the spokeDevices 
-   * NetDeviceContainer.  A point-to-point channel is created for each spoke.
-   *
-   * The ordering of the devices in the hubDevices container is according to
-   * the order of the spokes container -- that is, hubDevices[0] will be the
-   * net device used on the hub that talks to spokes[0].  the container entry
-   * spokeDevices[0] will have the device that hubDevices[0] talks to -- those
-   * two devices are the ones that connect hub to spokes[0].
-   *
-   * \param hubName The name of the central node of the star network
-   * \param spokes A NodeContainer of the nodes that will be the spoke (leaf)
-   *               nodes
-   * \param hubDevices A NetDeviceContainer that will be filled with pointers
-   *                   to the point-to-point net devices created on the hub.
-   * \param spokeDevices A NetDeviceContainer that will be filled with pointers
-   *                    to the point-to-point net devices created on each of 
-   *                    the spokes.
-   */
-  void InstallStar (std::string hubName, NodeContainer spokes, 
-                    NetDeviceContainer& hubDevices, NetDeviceContainer& spokeDevices);
-
 private:
   void EnablePcap (Ptr<Node> node, Ptr<NetDevice> device, Ptr<Queue> queue);
   static void SniffEvent (Ptr<PcapWriter> writer, Ptr<const Packet> packet);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/point-to-point-star-helper.cc	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,159 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+#include <iostream>
+#include <sstream>
+
+// ns3 includes
+#include "ns3/animation-interface.h"
+#include "ns3/point-to-point-star-helper.h"
+#include "ns3/canvas-location.h"
+
+#include "ns3/node-list.h"
+#include "ns3/point-to-point-net-device.h"
+#include "ns3/vector.h"
+
+NS_LOG_COMPONENT_DEFINE("PointToPointStarHelper");
+
+namespace ns3 {
+  
+PointToPointStarHelper::PointToPointStarHelper (uint32_t numSpokes,
+                   PointToPointHelper p2pHelper)
+{
+  m_hub.Create (1);
+  m_spokes.Create (numSpokes);
+
+  for (uint32_t i = 0; i < m_spokes.GetN (); ++i)
+    {
+      NetDeviceContainer nd = p2pHelper.Install (m_hub.Get (0), m_spokes.Get (i));
+      m_hubDevices.Add (nd.Get (0));
+      m_spokeDevices.Add (nd.Get (1));
+    }
+}
+
+PointToPointStarHelper::~PointToPointStarHelper ()
+{}
+
+Ptr<Node> 
+PointToPointStarHelper::GetHub () const
+{
+  return m_hub.Get (0);
+}
+
+Ptr<Node> 
+PointToPointStarHelper::GetSpoke (uint32_t i) const
+{
+  return m_spokes.Get (i);
+}
+
+Ipv4Address 
+PointToPointStarHelper::GetHubIpv4Address (uint32_t i) const
+{
+  return m_hubInterfaces.GetAddress (i);
+}
+
+Ipv4Address 
+PointToPointStarHelper::GetSpokeIpv4Address (uint32_t i) const
+{
+  return m_spokeInterfaces.GetAddress (i);
+}
+
+uint32_t  
+PointToPointStarHelper::SpokeCount () const
+{
+  return m_spokes.GetN ();
+}
+
+void 
+PointToPointStarHelper::InstallStack (InternetStackHelper stack)
+{
+  stack.Install (m_hub);
+  stack.Install (m_spokes);
+}
+
+void 
+PointToPointStarHelper::AssignIpv4Addresses (Ipv4AddressHelper address)
+{
+  for (uint32_t i = 0; i < m_spokes.GetN (); ++i)
+    {
+      m_hubInterfaces.Add (address.Assign (m_hubDevices.Get (i)));
+      m_spokeInterfaces.Add (address.Assign (m_spokeDevices.Get (i)));
+      address.NewNetwork ();
+    }
+}
+
+void 
+PointToPointStarHelper::BoundingBox (double ulx, double uly,
+                                     double lrx, double lry)
+{
+  double xDist;
+  double yDist;
+  if (lrx > ulx)
+    {
+      xDist = lrx - ulx;
+    }
+  else
+    {
+      xDist = ulx - lrx;
+    }
+  if (lry > uly)
+    {
+      yDist = lry - uly;
+    }
+  else
+    {
+      yDist = uly - lry;
+    }
+
+  // Place the hub
+  Ptr<Node> hub = m_hub.Get (0);
+  Ptr<CanvasLocation> hubLoc =  hub->GetObject<CanvasLocation> ();
+  if (hubLoc == 0)
+    {
+      hubLoc = CreateObject<CanvasLocation> ();
+      hub->AggregateObject (hubLoc);
+    }
+  Vector hubVec (ulx + xDist/2.0, uly + yDist/2.0, 0);
+  hubLoc->SetLocation (hubVec);
+
+  double spokeDist;
+  if (xDist > yDist)
+    {
+      spokeDist = yDist/4.0;
+    }
+  else
+    {
+      spokeDist = xDist/4.0;
+    }
+
+  double theta = 2*M_PI/m_spokes.GetN ();
+  for (uint32_t i = 0; i < m_spokes.GetN (); ++i)
+    {
+      Ptr<Node> spokeNode = m_spokes.Get (i);
+      Ptr<CanvasLocation> spokeLoc = spokeNode->GetObject<CanvasLocation> ();
+      if (spokeLoc == 0)
+        {
+          spokeLoc = CreateObject<CanvasLocation> ();
+          spokeNode->AggregateObject (spokeLoc);
+        }
+        Vector spokeVec (hubVec.x + cos (theta*i) * spokeDist, 
+                         hubVec.y + sin (theta*i) * spokeDist,
+                         0);
+        spokeLoc->SetLocation (spokeVec);
+    }
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/helper/point-to-point-star-helper.h	Tue Nov 24 10:16:58 2009 -0500
@@ -0,0 +1,58 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation;
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+// Define an object to create a dumbbell topology.
+
+#ifndef POINT_TO_POINT_STAR_HELPER_H
+#define POINT_TO_POINT_STAR_HELPER_H
+
+#include <string>
+
+#include "point-to-point-helper.h"
+#include "ipv4-address-helper.h"
+#include "internet-stack-helper.h"
+#include "ipv4-interface-container.h"
+
+namespace ns3 {
+  
+class PointToPointStarHelper
+{
+public:
+  PointToPointStarHelper (uint32_t numSpokes, 
+                          PointToPointHelper p2pHelper);
+  ~PointToPointStarHelper ();
+public:
+  Ptr<Node> GetHub () const;
+  Ptr<Node> GetSpoke (uint32_t) const;
+  Ipv4Address GetHubIpv4Address (uint32_t) const;
+  Ipv4Address GetSpokeIpv4Address (uint32_t) const;
+  uint32_t SpokeCount () const;
+  void InstallStack (InternetStackHelper stack);
+  void AssignIpv4Addresses (Ipv4AddressHelper address);
+  void BoundingBox (double, double, double, double);
+
+private:
+  NodeContainer m_hub;
+  NetDeviceContainer m_hubDevices;
+  NodeContainer m_spokes;
+  NetDeviceContainer m_spokeDevices;
+  Ipv4InterfaceContainer m_hubInterfaces;
+  Ipv4InterfaceContainer m_spokeInterfaces;
+};
+}
+#endif
+
+
--- a/src/helper/wscript	Tue Nov 24 14:00:39 2009 +0100
+++ b/src/helper/wscript	Tue Nov 24 10:16:58 2009 -0500
@@ -41,6 +41,12 @@
         'ipv6-routing-helper.cc',
         'ping6-helper.cc',
         'flow-monitor-helper.cc',
+        'animation-interface.cc',
+        'canvas-location.cc',
+        'point-to-point-dumbbell-helper.cc',
+        'point-to-point-grid-helper.cc',
+        'point-to-point-star-helper.cc',
+        'csma-star-helper.cc',
         ]
 
     headers = bld.new_task_gen('ns3header')
@@ -85,6 +91,12 @@
         'ipv6-routing-helper.h',
         'ping6-helper.h',
         'flow-monitor-helper.h',
+        'animation-interface.h',
+        'canvas-location.h',
+        'point-to-point-dumbbell-helper.h',
+        'point-to-point-grid-helper.h',
+        'point-to-point-star-helper.h',
+        'csma-star-helper.h',
         ]
 
     env = bld.env_of_name('default')
@@ -103,3 +115,8 @@
                 'tap-bridge-helper.h',
                 ])
 
+def configure(conf):
+    conf.check(header_name='sys/socket.h', define_name='HAVE_SYS_SOCKET_H')
+    conf.check(header_name='netinet/in.h', define_name='HAVE_NETINET_IN_H')
+    conf.write_config_header('ns3/net-anim-config.h', top=True)
+
--- a/src/wscript	Tue Nov 24 14:00:39 2009 +0100
+++ b/src/wscript	Tue Nov 24 10:16:58 2009 -0500
@@ -47,7 +47,6 @@
     'test/ns3tcp',
     'test/ns3wifi',
     'contrib/flow-monitor',
-    'contrib/net-anim',
     )
 
 def set_options(opt):
@@ -71,6 +70,7 @@
     conf.sub_config('devices/tap-bridge')
     conf.sub_config('contrib')
     conf.sub_config('internet-stack')
+    conf.sub_config('helper')
 
     blddir = os.path.abspath(os.path.join(conf.blddir, conf.env.variant()))
     conf.env.append_value('NS3_MODULE_PATH', blddir)