Initial import of energy model
authorHe Wu <mdzz@u.washington.edu>
Wed, 07 Jul 2010 21:54:32 -0700
changeset 6429 5ee11b58989d
parent 6428 a3afed368709
child 6430 cfbd2029c0ce
child 6506 1d64d3bac8ce
Initial import of energy model
AUTHORS
RELEASE_NOTES
src/contrib/energy/helper/basic-energy-source-helper.cc
src/contrib/energy/helper/basic-energy-source-helper.h
src/contrib/energy/helper/basic-radio-energy-model-helper.cc
src/contrib/energy/helper/basic-radio-energy-model-helper.h
src/contrib/energy/helper/energy-model-helper.cc
src/contrib/energy/helper/energy-model-helper.h
src/contrib/energy/model/basic-energy-source.cc
src/contrib/energy/model/basic-energy-source.h
src/contrib/energy/model/basic-radio-energy-model.cc
src/contrib/energy/model/basic-radio-energy-model.h
src/contrib/energy/model/device-energy-model.cc
src/contrib/energy/model/device-energy-model.h
src/contrib/energy/model/energy-source.cc
src/contrib/energy/model/energy-source.h
src/contrib/energy/model/radio-energy-model.cc
src/contrib/energy/model/radio-energy-model.h
src/contrib/energy/test/basic-energy-model-test.cc
src/contrib/energy/wscript
src/wscript
--- a/AUTHORS	Wed Jul 07 23:58:40 2010 +0900
+++ b/AUTHORS	Wed Jul 07 21:54:32 2010 -0700
@@ -37,6 +37,7 @@
 Fabian Mauchle (f1mauchl@hsr.ch)
 Andrey Mazo (mazo@iitp.ru)
 Faker Moatamri (faker.moatamri@sophia.inria.fr)
+Sidharth Nabar (snabar@uw.edu)
 Michael Nowatkowski (nowatkom@gmail.com)
 Duy Nguyen (duy@soe.ucsc.edu)
 Tommaso Pecorella (tommaso.pecorella@unifi.it)
@@ -63,3 +64,4 @@
 Tom Wambold (tom5760@gmail.com)
 Danqi Wang (beyondwdq@gmail.com)
 Florian Westphal (fw@strlen.de)
+He Wu (mdzz@u.washington.edu)
--- a/RELEASE_NOTES	Wed Jul 07 23:58:40 2010 +0900
+++ b/RELEASE_NOTES	Wed Jul 07 21:54:32 2010 -0700
@@ -45,6 +45,10 @@
    - A brand new NS-2 mobility trace reader supports BonnMotion, SUMO, TraNS, 
      etc. traces.
 
+   - An energy model for nodes and devices, including an energy source
+     model and device energy models allowing energy-aware devices
+     to notify the energy source about energy consumption.  
+
 Bugs fixed
 ----------
 The following lists many of the bugs that were fixed since ns-3.7, in
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/helper/basic-energy-source-helper.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,67 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#include "basic-energy-source-helper.h"
+#include "ns3/energy-source.h"
+
+namespace ns3 {
+
+BasicEnergySourceHelper::BasicEnergySourceHelper ()
+{
+  m_basicEnergySource.SetTypeId ("ns3::BasicEnergySource");
+}
+
+BasicEnergySourceHelper::~BasicEnergySourceHelper ()
+{
+}
+
+void
+BasicEnergySourceHelper::Set (std::string name, const AttributeValue &v)
+{
+  m_basicEnergySource.Set (name, v);
+}
+
+Ptr<EnergySource>
+BasicEnergySourceHelper::Create (void) const
+{
+  Ptr<EnergySource> source = m_basicEnergySource.Create<EnergySource> ();
+  NS_ASSERT (source != 0);
+  return source;
+}
+
+void
+BasicEnergySourceHelper::Install (Ptr<Node> node) const
+{
+  NS_ASSERT (node != NULL);
+  // check if energy source already exists
+  Ptr<EnergySource> source = node->GetObject<EnergySource> ();
+  if (source != NULL)
+    {
+      NS_FATAL_ERROR ("Energy source already installed!");
+      return;
+    }
+  // create energy source
+  source = Create ();
+  NS_ASSERT (source != NULL);
+  // aggregate source to node
+  node->AggregateObject (source);
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/helper/basic-energy-source-helper.h	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,52 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#ifndef BASIC_ENERGY_SOURCE_HELPER
+#define BASIC_ENERGY_SOURCE_HELPER
+
+#include "energy-model-helper.h"
+
+namespace ns3 {
+
+class Node;
+
+/**
+ * \brief Creates a BasicEnergySource object.
+ */
+class BasicEnergySourceHelper : public EnergySourceHelper
+{
+public:
+  BasicEnergySourceHelper ();
+  ~BasicEnergySourceHelper ();
+
+  void Set (std::string name, const AttributeValue &v);
+
+  Ptr<EnergySource> Create (void) const;
+
+  void Install (Ptr<Node> node) const;
+
+private:
+  ObjectFactory m_basicEnergySource;
+
+};
+
+} // namespace ns3
+
+#endif  /* BASIC_ENERGY_SOURCE_HELPER */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/helper/basic-radio-energy-model-helper.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,96 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#include "basic-radio-energy-model-helper.h"
+#include "basic-energy-source-helper.h"
+#include "ns3/radio-energy-model.h"
+#include "ns3/config.h"
+#include "ns3/names.h"
+#include "ns3/log.h"
+
+namespace ns3 {
+
+NS_LOG_COMPONENT_DEFINE ("BasicRadioEnergyModelHelper");
+
+BasicRadioEnergyModelHelper::BasicRadioEnergyModelHelper ()
+{
+  m_radioEnergy.SetTypeId ("ns3::BasicRadioEnergyModel");
+  m_depletionCallback.Nullify ();
+}
+
+BasicRadioEnergyModelHelper::~BasicRadioEnergyModelHelper ()
+{
+}
+
+void
+BasicRadioEnergyModelHelper::Set (std::string name, const AttributeValue &v)
+{
+  m_radioEnergy.Set (name, v);
+}
+
+Ptr<DeviceEnergyModel>
+BasicRadioEnergyModelHelper::Create (void) const
+{
+  return m_radioEnergy.Create<DeviceEnergyModel> ();
+}
+
+void
+BasicRadioEnergyModelHelper::SetDepletionCallback (
+  BasicRadioEnergyModel::BasicEnergyDepletionCallback callback)
+{
+  m_depletionCallback = callback;
+}
+
+/*
+ * Private function starts here.
+ */
+
+void
+BasicRadioEnergyModelHelper::DoInstall (Ptr<Node> node) const
+{
+  NS_LOG_FUNCTION (this << node);
+  // check if energy source is installed
+  Ptr<EnergySource> source = node->GetObject<EnergySource> ();
+  if (source != NULL)
+    {
+      Ptr<BasicRadioEnergyModel> model = m_radioEnergy.Create ()->
+        GetObject<BasicRadioEnergyModel> ();
+      if (model == NULL)
+        {
+          NS_FATAL_ERROR ( "The requested radio energy model does not exist: "
+                           << m_radioEnergy.GetTypeId ().GetName ());
+        }
+      else
+        {
+          // set energy source pointer
+          model->SetEnergySource (source);
+          // set energy depletion callback
+          model->SetEnergyDepletionCallback (m_depletionCallback);
+          // add model to device model list in energy source
+          source->AppendDeviceEnergyModel (model);
+        }
+    }
+  else
+    {
+      NS_FATAL_ERROR ("Energy source NOT installed!");
+    }
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/helper/basic-radio-energy-model-helper.h	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,90 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+* Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+*
+* 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: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+*/
+
+#ifndef BASIC_RADIO_ENERGY_MODEL_HELPER_H
+#define BASIC_RADIO_ENERGY_MODEL_HELPER_H
+
+#include "energy-model-helper.h"
+#include "ns3/device-energy-model.h"
+#include "ns3/basic-radio-energy-model.h"
+
+namespace ns3 {
+
+/**
+ * \brief Assign energy model to nodes.
+ *
+ * This installer is used for BasicRadioEnergyModel.
+ */
+class BasicRadioEnergyModelHelper : public DeviceEnergyModelHelper
+{
+public:
+  /**
+   * Construct a helper which is used to add a radio energy model to a node
+   */
+  BasicRadioEnergyModelHelper ();
+
+  /**
+   * Destroy a RadioEnergy Helper
+   */
+  ~BasicRadioEnergyModelHelper ();
+
+  /**
+   * \param name the name of the attribute to set
+   * \param v the value of the attribute
+   *
+   * Sets an attribute of the underlying PHY object.
+   */
+  void Set (std::string name, const AttributeValue &v);
+
+  /**
+   * \returns A newly created RadioEnergySource object.
+   */
+  Ptr<DeviceEnergyModel> Create (void) const;
+
+  /**
+   * \param callback Callback function for energy depletion handling.
+   *
+   * Sets the callback to be invoked when energy is depleted.
+   */
+  void SetDepletionCallback (
+    BasicRadioEnergyModel::BasicEnergyDepletionCallback callback);
+
+
+private:
+  /**
+   * \brief Add an energy model to the specified node.
+   *
+   * \param node The node on which the energy model is to be installed.
+   *
+   * This method creates an instance of a ns3::BasicRadioEnergyModel and
+   * aggregates it to the given node.
+   */
+  void DoInstall (Ptr<Node> node) const;
+
+private:
+  ObjectFactory m_radioEnergy;
+  /// Callback function for energy depletion.
+  BasicRadioEnergyModel::BasicEnergyDepletionCallback m_depletionCallback;
+
+};
+
+} // namespace ns3
+
+#endif /* BASIC_RADIO_ENERGY_MODEL_HELPER_H */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/helper/energy-model-helper.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,114 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#include "energy-model-helper.h"
+#include "ns3/log.h"
+#include "ns3/config.h"
+#include "ns3/names.h"
+
+namespace ns3 {
+
+/*
+ * EnergySourceHelper
+ */
+EnergySourceHelper::~EnergySourceHelper ()
+{
+}
+
+/*
+ * DeviceEnergyModelHelper
+ */
+DeviceEnergyModelHelper::~DeviceEnergyModelHelper ()
+{
+}
+
+void
+DeviceEnergyModelHelper::Install (Ptr<Node> node) const
+{
+  NS_ASSERT (node != NULL);
+  DoInstall (node);
+}
+
+void
+DeviceEnergyModelHelper::Install (NodeContainer c) const
+{
+  for (NodeContainer::Iterator i = c.Begin (); i != c.End (); ++i)
+    {
+      Install (*i);
+    }
+}
+
+void
+DeviceEnergyModelHelper::Install (std::string nodeName) const
+{
+  Ptr<Node> node = Names::Find<Node> (nodeName);
+  Install (node);
+}
+
+void
+DeviceEnergyModelHelper::InstallAll (void) const
+{
+  Install (NodeContainer::GetGlobal ());
+}
+
+/*
+ * EnergyModelHelper
+ */
+EnergyModelHelper::EnergyModelHelper ()
+{
+}
+
+void
+EnergyModelHelper::Install (const EnergySourceHelper &sourceHelper,
+                            const DeviceEnergyModelHelper &modelHelper, Ptr<Node> node) const
+{
+  NS_ASSERT (node != NULL);
+  // install source. source must be installed before installing device model.
+  sourceHelper.Install (node);
+  // install device model
+  modelHelper.Install (node);
+}
+
+void
+EnergyModelHelper::Install (const EnergySourceHelper &sourceHelper,
+                            const DeviceEnergyModelHelper &modelHelper, NodeContainer c) const
+{
+  for (NodeContainer::Iterator i = c.Begin (); i != c.End (); ++i)
+    {
+      Install (sourceHelper, modelHelper, *i);
+    }
+}
+
+void
+EnergyModelHelper::Install (const EnergySourceHelper &sourceHelper,
+                            const DeviceEnergyModelHelper &modelHelper, std::string nodeName) const
+{
+  Ptr<Node> node = Names::Find<Node> (nodeName);
+  Install (sourceHelper, modelHelper, node);
+}
+
+void
+EnergyModelHelper::InstallAll (const EnergySourceHelper &sourceHelper,
+                               const DeviceEnergyModelHelper &modelHelper) const
+{
+  Install (sourceHelper, modelHelper, NodeContainer::GetGlobal ());
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/helper/energy-model-helper.h	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,189 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#ifndef ENERGY_MODEL_HELPER
+#define ENERGY_MODEL_HELPER
+
+#include "ns3/attribute.h"
+#include "ns3/object-factory.h"
+#include "ns3/node-container.h"
+#include "ns3/ptr.h"
+#include "ns3/energy-source.h"
+#include "ns3/device-energy-model.h"
+
+namespace ns3 {
+
+/**
+ * \brief Creates EnergySource objects.
+ *
+ * This class creates and installs an energy source onto network nodes. This
+ * base class must be implemented by new EnergySource implementation which wish
+ * to integrate with the \ref ns3::EnergyModelHelper class.
+ */
+class EnergySourceHelper
+{
+public:
+  virtual ~EnergySourceHelper ();
+
+  /**
+   * \returns A newly created EnergySource object.
+   * Subclasses must implement this methods to allow the ns3::EnergySource class
+   * to create DeviceEnergyModel object for installation.
+   */
+  virtual Ptr<EnergySource> Create (void) const = 0;
+
+  /**
+   * \param node Pointer to the node where EnergySource will be installed on.
+   *
+   * This method installs an EnergySource onto a node. Must be implemented by
+   * subclasses.
+   */
+  virtual void Install (Ptr<Node> node) const = 0;
+
+};
+
+
+/**
+ * \brief Creates DeviceEnergyModel objects
+ *
+ * This class can help to create and install an DeviceEnergyModel onto network
+ * nodes. It can be called separately to install extra DeviceEnergyModels onto
+ * the same nodes. This base class must be implemented by new DeviceEnergyModel
+ * which wishes to integrate with the \ref ns3::EnergyModelHelper class.
+ *
+ * Note that DeviceEnergyModel objects are *not* aggregated onto the node. They
+ * can be accessed through the EnergySource object, which *is* aggregated onto
+ * the node.
+ */
+class DeviceEnergyModelHelper
+{
+public:
+  virtual ~DeviceEnergyModelHelper ();
+
+  /**
+   * \returns A newly created DeviceEnergySource object.
+   *
+   * Subclasses must implement this method to allow the ns3::DeviceEnergyModel
+   * class to create DeviceEnergyModel object for installation.
+   */
+  virtual Ptr<DeviceEnergyModel> Create (void) const = 0;
+
+  /**
+   * \param name Name of attribute to set.
+   * \param v Value of the attribute.
+   *
+   * Sets one of the attributes of underlying DeviceEnergyModel.
+   */
+  virtual void Set (std::string name, const AttributeValue &v) = 0;
+
+  /**
+   * \param node The node on which a DeviceEnergyModel object must be created.
+   *
+   * Installs an DeviceEnergyModel onto a node. Subclasses must implement this
+   * method.
+   */
+  void Install (Ptr<Node> node) const;
+
+  /**
+   * \param c The set of nodes on which a jammer object must be created.
+   *
+   * Installs DeviceEnergyModel onto a list of nodes. Calls Install (Ptr<Node>
+   * node).
+   */
+  void Install (NodeContainer c) const;
+
+  /**
+   * \param nodeName The name of node.
+   *
+   * Calls Install (Ptr<Node> node).
+   */
+  void Install (std::string nodeName) const;
+
+  /**
+   * Install on *ALL* nodes exists in simulation.
+   */
+  void InstallAll (void) const;
+
+
+private:
+  /**
+   * \param node The node on which a DeviceEnergyModel object must be created.
+   *
+   * Implements Install (Ptr<Node>). Subclasses must implement this method.
+   */
+  virtual void DoInstall (Ptr<Node> node) const = 0;
+
+};
+
+
+/**
+ * \brief Creates EnergySource and DeviceEnergyModel objects.
+ *
+ * This class helps to create EnergySource and DeviceEnergyModel objects. Note
+ * that only a single EnergySource can exist on the same node where multiple
+ * DeviceEnergyModel can coexist on the same node. Extra DeviceEnergyModels can
+ * be installed by DeviceEnergyModelHelper.
+ */
+class EnergyModelHelper
+{
+public:
+  /**
+   * Create an EnergyModelHelper in an empty state: all its parameters must be
+   * set before calling ns3::EnergyModelHelper::Install.
+   */
+  EnergyModelHelper ();
+
+  /**
+   * \param source The EnergySourceHelper to create EnergySource.
+   * \param model The DeviceEnergyModelHelper to create DeviceEnergyModel.
+   * \param node The node on which the energy model will be installed on.
+   */
+  void Install (const EnergySourceHelper &sourceHelper,
+                const DeviceEnergyModelHelper &modelHelper, Ptr<Node> node) const;
+
+  /**
+   * \param source The EnergySourceHelper to create EnergySource.
+   * \param model The DeviceEnergyModelHelper to create DeviceEnergyModel.
+   * \param node List of node on which the energy model will be installed on.
+   */
+  void Install (const EnergySourceHelper &sourceHelper,
+                const DeviceEnergyModelHelper &modelHelper, NodeContainer c) const;
+
+  /**
+   * \param source The EnergySourceHelper to create EnergySource.
+   * \param model The DeviceEnergyModelHelper to create DeviceEnergyModel.
+   * \param node name of node on which the energy model will be installed on.
+   */
+  void Install (const EnergySourceHelper &sourceHelper,
+                const DeviceEnergyModelHelper &modelHelper, std::string nodeName) const;
+
+  /**
+   * \param source The EnergySourceHelper to create EnergySource.
+   * \param model The DeviceEnergyModelHelper to create DeviceEnergyModel.
+   * \param node name of node on which the energy model will be installed on.
+   */
+  void InstallAll (const EnergySourceHelper &sourceHelper,
+                   const DeviceEnergyModelHelper &modelHelper) const;
+
+};
+
+} // namespace ns3
+
+#endif  /* ENERGY_MODEL_HELPER */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/basic-energy-source.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,133 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#include "basic-energy-source.h"
+#include "ns3/log.h"
+#include "ns3/assert.h"
+#include "ns3/double.h"
+#include "ns3/trace-source-accessor.h"
+
+NS_LOG_COMPONENT_DEFINE ("BasicEnergySource");
+
+namespace ns3 {
+
+NS_OBJECT_ENSURE_REGISTERED (BasicEnergySource);
+
+TypeId
+BasicEnergySource::GetTypeId (void)
+{
+  static TypeId tid = TypeId ("ns3::BasicEnergySource")
+    .SetParent<EnergySource> ()
+    .AddConstructor<BasicEnergySource> ()
+    .AddAttribute ("BasicEnergySourceInitialEnergyJ",
+                   "Initial energy stored in basic energy source.",
+                   DoubleValue (10),  // in Joules
+                   MakeDoubleAccessor (&BasicEnergySource::SetInitialEnergy,
+                                       &BasicEnergySource::DoGetInitialEnergy),
+                   MakeDoubleChecker<double> ())
+    .AddTraceSource ("RemainingEnergy",
+                     "Remaining energy at BasicEnergySource.",
+                     MakeTraceSourceAccessor (&BasicEnergySource::m_remainingEnergyJ))
+  ;
+  return tid;
+}
+
+BasicEnergySource::BasicEnergySource ()
+{
+}
+
+BasicEnergySource::~BasicEnergySource ()
+{
+}
+
+void
+BasicEnergySource::SetInitialEnergy (double initialEnergyJ)
+{
+  NS_LOG_FUNCTION (this << initialEnergyJ);
+  NS_ASSERT (initialEnergyJ >= 0);
+  m_initialEnergyJ = initialEnergyJ;
+  // set remaining energy to be initial energy
+  m_remainingEnergyJ = m_initialEnergyJ;
+}
+
+/*
+ * Private functions start here.
+ */
+
+void
+BasicEnergySource::DoDispose (void)
+{
+  NS_LOG_FUNCTION (this);
+  BreakDeviceEnergyModelRefCycle ();  // break reference cycle
+}
+
+double
+BasicEnergySource::DoGetInitialEnergy (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_initialEnergyJ;
+}
+
+double
+BasicEnergySource::DoGetRemainingEnergy (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_remainingEnergyJ;
+}
+
+void
+BasicEnergySource::DoDecreaseRemainingEnergy (double energyJ)
+{
+  NS_LOG_FUNCTION (this << energyJ);
+  NS_ASSERT (energyJ >= 0);
+  m_remainingEnergyJ -= energyJ;
+  // check if remaining energy is 0
+  if (m_remainingEnergyJ <= 0)
+    {
+      HandleEnergyDrainedEvent ();
+    }
+}
+
+void
+BasicEnergySource::HandleEnergyDrainedEvent (void)
+{
+  NS_LOG_FUNCTION (this);
+  NS_LOG_DEBUG ("BasicEnergySource:Energy depleted!");
+  NotifyEnergyDrained (); // notify DeviceEnergyModel objects
+  // energy never goes below 0
+  m_remainingEnergyJ = 0;
+}
+
+void
+BasicEnergySource::DoIncreaseRemainingEnergy (double energyJ)
+{
+  NS_LOG_FUNCTION (this << energyJ);
+  NS_ASSERT (energyJ >= 0);
+  m_remainingEnergyJ += energyJ;
+}
+
+double
+BasicEnergySource::DoGetEnergyFraction (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_remainingEnergyJ / m_initialEnergyJ;
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/basic-energy-source.h	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,95 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#ifndef BASIC_ENERGY_SOURCE
+#define BASIC_ENERGY_SOURCE
+
+#include "ns3/traced-value.h"
+#include "energy-source.h"
+
+namespace ns3 {
+
+class BasicEnergySource : public EnergySource
+{
+public:
+  static TypeId GetTypeId (void);
+  BasicEnergySource ();
+  virtual ~BasicEnergySource ();
+
+
+  /**
+   * \param initialEnergy Initial energy, in Joules
+   *
+   * Implements SetInitialEnergy. Note that initial energy is assumed to be set
+   * before simulation starts and is set only once per simulation.
+   */
+  void SetInitialEnergy (double initialEnergyJ);
+
+
+private:
+  void DoDispose (void);
+
+  /**
+   * \return Initial energy stored in energy source, in Joules.
+   *
+   * Implements GetInitialEnergy.
+   */
+  double DoGetInitialEnergy (void) const;
+
+  /**
+   * \return Remaining energy in energy source, in Joules
+   *
+   * Implements GetRemainingEnergy.
+   */
+  double DoGetRemainingEnergy (void) const;
+
+  /**
+   * \param energy Amount of energy (in Joules) to decrease from energy source.
+   *
+   * Implements DecreaseRemainingEnergy.
+   */
+  void DoDecreaseRemainingEnergy (double energyJ);
+
+  /**
+   * Handles the remaining energy going to zero event. This function notifies
+   * all the energy models aggregated to the node about the energy being
+   * depleted. Each energy model is then responsible for its own handler.
+   */
+  void HandleEnergyDrainedEvent (void);
+
+  /**
+   * \param energy Amount of energy (in Joules) to increase from energy source.
+   *
+   * Implements IncreaseRemainingEnergy.
+   */
+  void DoIncreaseRemainingEnergy (double energyJ);
+
+  /// Implements GetEnergyFraction.
+  double DoGetEnergyFraction (void) const;
+
+private:
+  double m_initialEnergyJ;                // initial energy, in Joules
+  TracedValue<double> m_remainingEnergyJ; // remaining energy, in Joules
+
+};
+
+} // namespace ns3
+
+#endif /* BASIC_ENERGY_SOURCE */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/basic-radio-energy-model.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,312 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#include "ns3/log.h"
+#include "ns3/double.h"
+#include "ns3/simulator.h"
+#include "ns3/trace-source-accessor.h"
+#include "basic-radio-energy-model.h"
+
+NS_LOG_COMPONENT_DEFINE ("BasicRadioEnergyModel");
+
+namespace ns3 {
+
+NS_OBJECT_ENSURE_REGISTERED (BasicRadioEnergyModel);
+
+TypeId
+BasicRadioEnergyModel::GetTypeId (void)
+{
+  static TypeId tid = TypeId ("ns3::BasicRadioEnergyModel")
+    .SetParent<RadioEnergyModel> ()
+    .AddConstructor<BasicRadioEnergyModel> ()
+    .AddAttribute ("TxPowerW",
+                   "The radio Tx power in Watts.",
+                   DoubleValue (0.0435),    // typical CC2420 value
+                   MakeDoubleAccessor (&BasicRadioEnergyModel::SetTxPowerW,
+                                       &BasicRadioEnergyModel::GetTxPowerW),
+                   MakeDoubleChecker<double> ())
+    .AddAttribute ("RxPowerW",
+                   "The radio Rx power in Watts.",
+                   DoubleValue (0.047),     // typical CC2420 value
+                   MakeDoubleAccessor (&BasicRadioEnergyModel::SetRxPowerW,
+                                       &BasicRadioEnergyModel::GetRxPowerW),
+                   MakeDoubleChecker<double> ())
+    .AddAttribute ("IdlePowerW",
+                   "The default radio Idle power in Watts.",
+                   DoubleValue (0.001065),  // typical CC2420 value
+                   MakeDoubleAccessor (&BasicRadioEnergyModel::SetIdlePowerW,
+                                       &BasicRadioEnergyModel::GetIdlePowerW),
+                   MakeDoubleChecker<double> ())
+    .AddAttribute ("SleepPowerW",
+                   "The default radio Sleep power in Watts.",
+                   DoubleValue (0.00005),   // typical CC2420 value
+                   MakeDoubleAccessor (&BasicRadioEnergyModel::SetSleepPowerW,
+                                       &BasicRadioEnergyModel::GetSleepPowerW),
+                   MakeDoubleChecker<double> ())
+    .AddAttribute ("PeriodicEnergyUpdateInterval",
+                   "Time between two consecutive periodic energy updates.",
+                   TimeValue (Seconds (1.0)),
+                   MakeTimeAccessor (&BasicRadioEnergyModel::SetEnergyUpdateInterval,
+                                     &BasicRadioEnergyModel::GetEnergyUpdateInterval),
+                   MakeTimeChecker ())
+    .AddTraceSource ("TotalEnergyConsumption",
+                     "Total energy consumption of the radio device.",
+                     MakeTraceSourceAccessor (&BasicRadioEnergyModel::m_totalEnergyConsumption))
+  ; 
+  return tid;
+}
+
+BasicRadioEnergyModel::BasicRadioEnergyModel ()
+{
+  NS_LOG_FUNCTION (this);
+  m_currentState = IDLE;
+  m_lastUpdateTime = Seconds (0.0);
+  m_energyDepletionCallback.Nullify ();
+  /*
+   * Start scheduling the periodic energy update event. BasicRadioEnergyModel
+   * is *not* aggregated to the node. Hence we have to schedule this in the
+   * constructor instead of calling it in DoStart.
+   */
+  m_periodicEnergyUpdateEvent = Simulator::Schedule (Seconds (0.0),
+                                                     &BasicRadioEnergyModel::DoUpdateRemainingEnergy, this, m_currentState);
+}
+
+BasicRadioEnergyModel::~BasicRadioEnergyModel ()
+{
+}
+
+BasicRadioEnergyModel::RadioState
+BasicRadioEnergyModel::GetCurrentState (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_currentState;
+}
+
+void
+BasicRadioEnergyModel::SetCurrentState (const RadioState currentState)
+{
+  NS_LOG_FUNCTION (this);
+  if (currentState != m_currentState)
+    {
+      m_currentState = currentState;
+      std::string stateName;
+      switch (currentState)
+        {
+        case TX:
+          stateName = "TX";
+          break;
+        case RX:
+          stateName = "RX";
+          break;
+        case IDLE:
+          stateName = "IDLE";
+          break;
+        case SLEEP:
+          stateName = "SLEEP";
+          break;
+        }
+      NS_LOG_DEBUG ("BasicRadioEnergyModel: Switching to state: "
+                    << stateName << " at time = " << Simulator::Now ());
+    }
+}
+
+Time
+BasicRadioEnergyModel::GetEnergyUpdateInterval (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_energyUpdateInterval;
+}
+
+void
+BasicRadioEnergyModel::SetEnergyUpdateInterval (const Time interval)
+{
+  NS_LOG_FUNCTION (this);
+  NS_ASSERT (interval.GetSeconds () > 0);
+  m_energyUpdateInterval = interval;
+}
+
+void
+BasicRadioEnergyModel::SetEnergyDepletionCallback (
+  BasicEnergyDepletionCallback callback)
+{
+  NS_LOG_FUNCTION (this);
+  if (callback.IsNull ())
+    {
+      NS_LOG_DEBUG ("BasicRadioEnergyModel:Setting NULL energy depletion callback!");
+    }
+  m_energyDepletionCallback = callback;
+}
+
+bool
+BasicRadioEnergyModel::IsStateTransitionValid (const RadioState destState)
+{
+  NS_LOG_FUNCTION (this << destState);
+  bool returnValue = true;
+
+  /*
+   * This is a placeholder function to specify if some of the radio state
+   * transitions are prohibited. For example, if transition TX -> RX is not
+   * allowed, and must go through IDLE as TX -> IDLE -> RX, then this method
+   * can be used to raise an ns3 error. Initial state is m_currentState.
+   */
+
+  return returnValue;
+}
+
+/*
+ * Private functions start here.
+ */
+
+void
+BasicRadioEnergyModel::DoDispose (void)
+{
+  NS_LOG_FUNCTION (this);
+  BreakSourceRefCycle (); // break reference cycle to energy source
+  m_energyDepletionCallback.Nullify ();
+}
+
+void
+BasicRadioEnergyModel::DoHandleEnergyDepletion (void)
+{
+  NS_LOG_FUNCTION (this);
+  NS_LOG_DEBUG ("BasicRadioEnergyModel:Energy is depleted!");
+  // invoke energy depletion callback, if set.
+  if (!m_energyDepletionCallback.IsNull ())
+    {
+      m_energyDepletionCallback ();
+    }
+}
+
+double
+BasicRadioEnergyModel::DoGetTotalEnergyConsumption (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_totalEnergyConsumption;
+}
+
+double
+BasicRadioEnergyModel::DoGetTxPowerW (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_txPower;
+}
+
+void 
+BasicRadioEnergyModel::DoSetTxPowerW (double txPowerW)
+{
+  NS_LOG_FUNCTION (this << txPowerW);
+  m_txPower = txPowerW;
+}
+
+double
+BasicRadioEnergyModel::DoGetRxPowerW (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_rxPower;
+}
+
+void 
+BasicRadioEnergyModel::DoSetRxPowerW (double rxPowerW)
+{
+  NS_LOG_FUNCTION (this << rxPowerW);
+  m_rxPower = rxPowerW;
+}
+
+double
+BasicRadioEnergyModel::DoGetIdlePowerW (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_idlePower;
+}
+
+void 
+BasicRadioEnergyModel::DoSetIdlePowerW (double idlePowerW)
+{
+  NS_LOG_FUNCTION (this << idlePowerW);
+  m_idlePower = idlePowerW;
+}
+
+double
+BasicRadioEnergyModel::DoGetSleepPowerW (void) const
+{
+  NS_LOG_FUNCTION (this);
+  return m_sleepPower;
+}
+
+void 
+BasicRadioEnergyModel::DoSetSleepPowerW (double sleepPowerW)
+{
+  NS_LOG_FUNCTION (this << sleepPowerW);
+  m_sleepPower = sleepPowerW;
+}
+
+void
+BasicRadioEnergyModel::DoUpdateRemainingEnergy (const RadioState destState)
+{
+  NS_LOG_FUNCTION (this << destState);
+  NS_ASSERT (IsStateTransitionValid (destState));
+
+  // Cancel the currently scheduled periodic event, if any
+  m_periodicEnergyUpdateEvent.Cancel ();
+
+  Time duration = Simulator::Now () - m_lastUpdateTime;
+  NS_ASSERT (duration.GetNanoSeconds () >= 0); // check if duration is valid
+
+  // update remaining energy accordingly
+  double energyToDecrease = 0.0;
+  switch (m_currentState)
+    {
+    case TX:
+      energyToDecrease = duration.GetSeconds () * m_txPower;
+      DecreaseRemainingEnergy (energyToDecrease);
+      break;
+    case RX:
+      energyToDecrease = duration.GetSeconds () * m_rxPower;
+      DecreaseRemainingEnergy (energyToDecrease);
+      break;
+    case IDLE:
+      energyToDecrease = duration.GetSeconds () * m_idlePower;
+      DecreaseRemainingEnergy (energyToDecrease);
+      break;
+    case SLEEP:
+      energyToDecrease = duration.GetSeconds () * m_sleepPower;
+      DecreaseRemainingEnergy (energyToDecrease);
+      break;
+    }
+
+  // update total energy consumption
+  m_totalEnergyConsumption += energyToDecrease;
+
+  // update last update time stamp
+  m_lastUpdateTime = Simulator::Now ();
+
+  // update current state & last update time stamp
+  SetCurrentState (destState);
+
+  // Schedule the next periodic energy update event
+  m_periodicEnergyUpdateEvent = Simulator::Schedule (m_energyUpdateInterval,
+                                                     &BasicRadioEnergyModel::DoUpdateRemainingEnergy, this, m_currentState);
+
+  // some debug message
+  NS_LOG_DEBUG ("BasicRadioEnergyModel:Total energy consumption is "
+                << m_totalEnergyConsumption << "J");
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/basic-radio-energy-model.h	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,159 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#ifndef BASIC_RADIO_ENERGY_MODEL_H
+#define BASIC_RADIO_ENERGY_MODEL_H
+
+#include "radio-energy-model.h"
+#include "ns3/nstime.h"
+#include "ns3/event-id.h"
+#include "ns3/traced-value.h"
+
+namespace ns3 {
+
+/**
+ * \brief a basic radio energy model
+ *
+ * This is a child class of the RadioEnergyModel class.
+ * 
+ * 4 states are defined for the radio: TX, RX, IDLE, SLEEP. Default state is
+ * IDLE.
+ * The different types of transactions that are defined are: 
+ *  1. Tx: State goes from IDLE to TX, radio is in TX state for TX_duration,
+ *     then state goes from TX to IDLE.
+ *  2. Rx: State goes from IDLE to RX, radio is in RX state for RX_duration,
+ *     then state goes from RX to IDLE.
+ *  3. Go_to_Sleep: State goes from IDLE to SLEEP.
+ *  4. End_of_Sleep: State goes from SLEEP to IDLE.
+ * The class keeps track of what state the radio is currently in.
+ *
+ * Energy calculation: For each transaction, we see how much time the radio
+ * spent in each state and calculate energy consumption accordingly.
+ *
+ * Energy update: Remaining energy =
+ *                Previous remaining energy - Energy_transaction.
+ *
+ * Default values for power consumption are based on CC2420 radio chip, with
+ * supply voltage as 2.5V and currents as 17.4 mA (TX), 18.8 mA (RX), 20 uA
+ * (sleep) and 426 uA (idle).
+ *
+ * TODO change default values to wifi radio chip numbers.
+ */
+class BasicRadioEnergyModel : public RadioEnergyModel
+{
+public:
+  /// Callback type for energy depletion handling.
+  typedef Callback<void> BasicEnergyDepletionCallback;
+
+public:
+  static TypeId GetTypeId (void);
+  BasicRadioEnergyModel ();
+  virtual ~BasicRadioEnergyModel ();
+
+  /**
+   * For current state, the getter is public, but the setter method should be
+   * private.
+   */
+  RadioState GetCurrentState (void) const;
+
+  /**
+   * \param interval Energy update interval.
+   *
+   * Setter for the energy update interval - time between two consecutive energy
+   * updates.
+   */
+  void SetEnergyUpdateInterval (const Time interval);
+
+  /**
+   * Getter for the energy update interval - time between two consecutive energy
+   * updates.
+   */
+  Time GetEnergyUpdateInterval (void) const;
+
+  /**
+   * \param callback Callback function.
+   *
+   * Sets callback for energy depletion handling.
+   */
+  void SetEnergyDepletionCallback (BasicEnergyDepletionCallback callback);
+
+  /**
+   * \param destState Radio state to switch to.
+   * \return True if the transition is allowed.
+   *
+   * This function checks if a given radio state transition is allowed.
+   */
+  bool IsStateTransitionValid (const RadioState destState);
+
+
+private:
+  void DoDispose (void);
+
+  /// Handles energy depletion.
+  void DoHandleEnergyDepletion (void);
+
+  /// Implements GetTotalEnergyConsumption.
+  double DoGetTotalEnergyConsumption (void) const;
+
+  double DoGetTxPowerW (void) const;
+  void DoSetTxPowerW (double txPowerW);
+  double DoGetRxPowerW (void) const;
+  void DoSetRxPowerW (double rxPowerW);
+  double DoGetIdlePowerW (void) const;
+  void DoSetIdlePowerW (double idlePowerW);
+  double DoGetSleepPowerW (void) const;
+  void DoSetSleepPowerW (double sleepPowerW);
+
+  void DoUpdateRemainingEnergy (const RadioState destState);
+
+  /**
+   * \param currentState New state the radio device is currently in.
+   *
+   * Sets current state. This function is private so that only the energy model
+   * can change its own state.
+   */
+  void SetCurrentState (const RadioState currentState);
+
+private:
+  /*
+   * Member variables for the power consumption in different radio modes.
+   * Power = (supply voltage * current draw)
+   */
+  double m_txPower;
+  double m_rxPower;
+  double m_idlePower;
+  double m_sleepPower;
+
+  // This variable keeps track of the total energy consumed by this particular model.
+  TracedValue<double> m_totalEnergyConsumption;
+
+  // State variables.
+  RadioState m_currentState;  // current state the radio is in
+  Time m_lastUpdateTime;      // time stamp of previous energy update
+  EventId m_periodicEnergyUpdateEvent;  // scheduled event to update remaining energy periodically
+  Time m_energyUpdateInterval;  // Time between consecutive periodic energy updates.
+
+  // energy depletion callback
+  BasicEnergyDepletionCallback m_energyDepletionCallback;
+};
+
+} // namespace ns3
+
+#endif /* BASIC_RADIO_ENERGY_MODEL_H */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/device-energy-model.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,99 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#include "device-energy-model.h"
+#include "ns3/log.h"
+
+NS_LOG_COMPONENT_DEFINE ("DeviceEnergyModel");
+
+namespace ns3 {
+
+NS_OBJECT_ENSURE_REGISTERED (DeviceEnergyModel);
+
+TypeId
+DeviceEnergyModel::GetTypeId (void)
+{
+  static TypeId tid = TypeId ("ns3::DeviceEnergyModel")
+    .SetParent<Object> ()
+  ;
+  return tid;
+}
+
+DeviceEnergyModel::DeviceEnergyModel ()
+{
+}
+
+DeviceEnergyModel::~DeviceEnergyModel ()
+{
+}
+
+void
+DeviceEnergyModel::HandleEnergyDepletion (void)
+{
+  DoHandleEnergyDepletion ();
+}
+
+void
+DeviceEnergyModel::SetEnergySource (Ptr<EnergySource> source)
+{
+  NS_LOG_FUNCTION (this << source);
+  NS_ASSERT (source != NULL);  // energy source must exist
+  m_energySourcePtr = source;
+}
+
+/*
+ * Private function starts here.
+ */
+
+void
+DeviceEnergyModel::DoDispose (void)
+{
+  NS_LOG_FUNCTION (this);
+  m_energySourcePtr = NULL;
+}
+
+/*
+ * Protected functions start here.
+ */
+
+void
+DeviceEnergyModel::DecreaseRemainingEnergy (double energyJ)
+{
+  NS_LOG_FUNCTION (this << energyJ);
+  NS_ASSERT (m_energySourcePtr != NULL);  // energy source must exist
+  m_energySourcePtr->DecreaseRemainingEnergy (energyJ);
+}
+
+void
+DeviceEnergyModel::IncreaseRemainingEnergy (double energyJ)
+{
+  NS_LOG_FUNCTION (this << energyJ);
+  NS_ASSERT (m_energySourcePtr != NULL);  // energy source must exist
+  m_energySourcePtr->IncreaseRemainingEnergy (energyJ);
+}
+
+void
+DeviceEnergyModel::BreakSourceRefCycle (void)
+{
+  NS_LOG_FUNCTION (this);
+  m_energySourcePtr = NULL;
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/device-energy-model.h	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,96 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#ifndef DEVICE_ENERGY_MODEL
+#define DEVICE_ENERGY_MODEL
+
+#include "ns3/object.h"
+#include "energy-source.h"
+
+namespace ns3 {
+
+class EnergySource;
+
+/**
+ * \brief Base class for device energy models.
+ *
+ * A device energy model should represent the energy consumption behavior of a
+ * specific device. It will update remaining energy stored in the EnergySource
+ * object installed on node. When energy is depleted, each DeviceEnergyModel
+ * object installed on the same node will be informed by the EnergySource.
+ */
+class DeviceEnergyModel : public Object
+{
+public:
+  static TypeId GetTypeId (void);
+  DeviceEnergyModel ();
+  virtual ~DeviceEnergyModel ();
+
+  /**
+   * This function is called by the EnergySource object when energy stored in
+   * the energy source is depleted. Should be implemented by child classes.
+   */
+  void HandleEnergyDepletion (void);
+
+  /// Sets the pointer to node energy source.
+  void SetEnergySource (Ptr<EnergySource> source);
+
+private:
+  /*
+   * Do not include DoStart in any child of this base class. DeviceEnergyModel
+   * is *not* aggregated to the node hence DoStart will *not* be called.
+   */
+
+  /**
+   * All child's implementation must call BreakSourceRefCycle to ensure
+   * reference cycle to EnergySource object is broken.
+   */
+  void DoDispose (void);
+
+  /// Implements HandleEnergyDepletion.
+  virtual void DoHandleEnergyDepletion (void) = 0;
+
+private:
+  /// Pointer to EnergySource object
+  Ptr<EnergySource> m_energySourcePtr;
+
+protected:
+  /// This function is used to access the private energy source pointer.
+  void DecreaseRemainingEnergy (double energyJ);
+
+  /// This function is used to access the private energy source pointer.
+  void IncreaseRemainingEnergy (double energyJ);
+
+  /**
+   * This function is called to break reference cycle between DeviceEnergyModel
+   * and EnergySource. Child of the DeviceEnergyModel base class must call this
+   * function in their implementation of DoDispose to make sure the reference
+   * cycle is broken.
+   *
+   * Normally this work will be completed by the DoDispose function. However it
+   * will be overridden in the child class. Hence we introduced this function.
+   */
+  void BreakSourceRefCycle (void);
+
+};
+
+}
+
+#endif /* DEVICE_ENERGY_MODEL */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/energy-source.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,157 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#include "energy-source.h"
+#include "ns3/log.h"
+
+NS_LOG_COMPONENT_DEFINE ("EnergySource");
+
+namespace ns3 {
+
+NS_OBJECT_ENSURE_REGISTERED (EnergySource);
+
+TypeId
+EnergySource::GetTypeId (void)
+{
+  static TypeId tid = TypeId ("ns3::EnergySource")
+    .SetParent<Object> ()
+  ;
+  return tid;
+}
+
+EnergySource::EnergySource ()
+{
+}
+
+EnergySource::~EnergySource ()
+{
+}
+
+double
+EnergySource::GetInitialEnergy (void) const
+{
+  return DoGetInitialEnergy ();
+}
+
+double
+EnergySource::GetRemainingEnergy (void) const
+{
+  return DoGetRemainingEnergy ();
+}
+
+void
+EnergySource::DecreaseRemainingEnergy (double energyJ)
+{
+  DoDecreaseRemainingEnergy (energyJ);
+}
+
+void
+EnergySource::IncreaseRemainingEnergy (double energyJ)
+{
+  DoIncreaseRemainingEnergy (energyJ);
+}
+
+double
+EnergySource::GetEnergyFraction (void) const
+{
+  return DoGetEnergyFraction ();
+}
+
+void
+EnergySource::AppendDeviceEnergyModel (
+  Ptr<DeviceEnergyModel> deviceEnergyModelPtr)
+{
+  NS_LOG_FUNCTION (this << deviceEnergyModelPtr);
+  NS_ASSERT (deviceEnergyModelPtr != NULL); // model must exist
+  m_deviceEnergyModelList.push_back (deviceEnergyModelPtr);
+}
+
+EnergySource::DeviceEnergyModelList
+EnergySource::FindDeviceEnergyModels (TypeId tid)
+{
+  NS_LOG_FUNCTION (this << tid);
+  DeviceEnergyModelList list;
+  DeviceEnergyModelList::iterator listItr;
+  for (listItr = m_deviceEnergyModelList.begin ();
+       listItr != m_deviceEnergyModelList.end (); listItr++)
+    {
+      if ((*listItr)->GetInstanceTypeId () == tid)
+        {
+          list.push_back (*listItr);
+        }
+    }
+  return list;
+}
+
+EnergySource::DeviceEnergyModelList
+EnergySource::FindDeviceEnergyModels (std::string name)
+{
+  NS_LOG_FUNCTION (this << name);
+  DeviceEnergyModelList list;
+  DeviceEnergyModelList::iterator listItr;
+  for (listItr = m_deviceEnergyModelList.begin ();
+       listItr != m_deviceEnergyModelList.end (); listItr++)
+    {
+      if ((*listItr)->GetInstanceTypeId ().GetName ().compare (name) == 0)
+        {
+          list.push_back (*listItr);
+        }
+    }
+  return list;
+}
+
+/*
+ * Private function starts here.
+ */
+
+void
+EnergySource::DoDispose (void)
+{
+  NS_LOG_FUNCTION (this);
+  m_deviceEnergyModelList.clear (); // break reference cycle
+}
+
+/*
+ * Protected functions start here.
+ */
+
+void
+EnergySource::NotifyEnergyDrained (void)
+{
+  NS_LOG_FUNCTION (this);
+  // notify all device energy models installed on node
+  DeviceEnergyModelList::iterator listItr;
+  for (listItr = m_deviceEnergyModelList.begin ();
+       listItr != m_deviceEnergyModelList.end (); listItr++)
+    {
+      NS_LOG_DEBUG ("BasicEnergySource:Notifying device energy model: "
+                    << (*listItr)->GetInstanceTypeId ());
+      (*listItr)->HandleEnergyDepletion ();
+    }
+}
+
+void
+EnergySource::BreakDeviceEnergyModelRefCycle (void)
+{
+  NS_LOG_FUNCTION (this);
+  m_deviceEnergyModelList.clear (); // break reference cycle
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/energy-source.h	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,158 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#ifndef ENERGY_SOURCE_H
+#define ENERGY_SOURCE_H
+
+#include "ns3/object.h"
+#include "ns3/ptr.h"
+#include "ns3/type-id.h"
+#include "device-energy-model.h"
+
+namespace ns3 {
+
+class DeviceEnergyModel;
+
+/**
+ * \brief Energy source base class.
+ *
+ * This is the base class for energy sources. Energy sources keep track of
+ * remaining energy. Device energy models will be updating the remaining energy
+ * in the energy source. The energy source itself does not update the remaining
+ * energy. Energy source also keeps a list of device energy models installed on
+ * the same node. When the remaining energy level reaches 0, the energy source
+ * will notify all device energy models stored in the list.
+ *
+ * Unit of energy is chosen as Joules since energy models typically calculate
+ * energy as (time in seconds * power in Watts). If the energy source stores
+ * energy in different units (eg. kWh), a simple converter function should
+ * suffice.
+ */
+class EnergySource : public Object
+{
+public:
+  /// List of pointers to DeviceEnergyModel objects.
+  typedef std::vector< Ptr<DeviceEnergyModel> > DeviceEnergyModelList;
+
+public:
+  static TypeId GetTypeId (void);
+  EnergySource ();
+  virtual ~EnergySource ();
+
+  /// This function returns initial energy stored in energy source.
+  double GetInitialEnergy (void) const;
+
+  /// This function returns the remaining energy stored in the energy source.
+  double GetRemainingEnergy (void) const;
+
+  /**
+   * \param energy Amount of energy to decrease (in Joules)
+   *
+   * This function decreases the remaining energy in the energy source by the
+   * specified amount.
+   */
+  void DecreaseRemainingEnergy (double energyJ);
+
+  /**
+   * \param energy Amount of energy to increase (in Joules)
+   *
+   * This function increases the remaining energy in the energy source by the
+   * specified amount. Provided for supporting re-charging or scavenging.
+   */
+  void IncreaseRemainingEnergy (double energyJ);
+
+  /**
+   * \return Energy fraction = remaining energy / initial energy [0, 1]
+   *
+   * This function returns the percentage of energy left in the energy source.
+   */
+  double GetEnergyFraction (void) const;
+
+  /**
+   * \param deviceEnergyModelPtr Pointer to device energy model.
+   * \param tid TypeId of the specific device energy model.
+   *
+   * This function appends a device energy model to the end of a list of
+   * DeviceEnergyModelInfo structs.
+   */
+  void AppendDeviceEnergyModel (Ptr<DeviceEnergyModel> deviceEnergyModelPtr);
+
+  /**
+   * \param tid TypeId of the DeviceEnergyModel we are searching for.
+   * \returns List of pointers to DeviceEnergyModel objects installed on node.
+   */
+  DeviceEnergyModelList FindDeviceEnergyModels (TypeId tid);
+  /**
+   * \param name name of the DeviceEnergyModel we are searching for.
+   * \returns List of pointers to DeviceEnergyModel objects installed on node.
+   */
+  DeviceEnergyModelList FindDeviceEnergyModels (std::string name);
+
+
+private:
+  /**
+   * All child's implementation must call BreakDeviceEnergyModelRefCycle to
+   * ensure reference cycles to DeviceEnergyModel objects are broken.
+   */
+  void DoDispose (void);
+
+  /// Implements GetInitialEnergy.
+  virtual double DoGetInitialEnergy (void) const = 0;
+
+  /// Implements GetRemainingEnergy.
+  virtual double DoGetRemainingEnergy (void) const = 0;
+
+  /// Implements DecreaseRemainingEnergy.
+  virtual void DoDecreaseRemainingEnergy (double energyJ) = 0;
+
+  /// Implements IncreaseRemainingEnergy.
+  virtual void DoIncreaseRemainingEnergy (double energyJ) = 0;
+
+  /// Implements GetEnergyFraction.
+  virtual double DoGetEnergyFraction (void) const = 0;
+
+private:
+  /// List of device energy models installed on the same node.
+  DeviceEnergyModelList m_deviceEnergyModelList;
+
+
+protected:
+  /**
+   * This function notifies all DeviceEnergyModel of energy depletion event. It
+   * is called by the child EnergySource class when energy depletion happens.
+   */
+  void NotifyEnergyDrained (void);
+
+  /**
+   * This function is called to break reference cycle between EnergySource and
+   * DeviceEnergyModel. Child of the EnergySource base class must call this
+   * function in their implementation of DoDispose to make sure the reference
+   * cycle is broken.
+   *
+   * Normally this work will be completed by the DoDispose function. However it
+   * will be overridden in the child class. Hence we introduced this function.
+   */
+  void BreakDeviceEnergyModelRefCycle (void);
+
+};
+
+} // namespace ns3
+
+#endif /* ENERGY_SOURCE_H */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/radio-energy-model.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,100 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#include "radio-energy-model.h"
+#include "ns3/log.h"
+
+NS_LOG_COMPONENT_DEFINE ("RadioEnergyModel");
+
+namespace ns3 {
+
+NS_OBJECT_ENSURE_REGISTERED (RadioEnergyModel);
+
+TypeId 
+RadioEnergyModel::GetTypeId (void)
+{
+  static TypeId tid = TypeId ("ns3::RadioEnergyModel")
+    .SetParent<DeviceEnergyModel> ()
+  ;
+  return tid;
+}
+
+RadioEnergyModel::RadioEnergyModel ()
+{
+}
+
+RadioEnergyModel::~RadioEnergyModel ()
+{
+}
+
+double
+RadioEnergyModel::GetTxPowerW (void) const
+{
+  return DoGetTxPowerW ();
+}
+double
+RadioEnergyModel::GetRxPowerW (void) const
+{
+  return DoGetRxPowerW ();
+}
+
+double
+RadioEnergyModel::GetIdlePowerW (void) const
+{
+  return DoGetIdlePowerW ();
+}
+
+double
+RadioEnergyModel::GetSleepPowerW (void) const
+{
+  return DoGetSleepPowerW ();
+}
+
+void 
+RadioEnergyModel::SetTxPowerW (double txPowerW)
+{
+  DoSetTxPowerW (txPowerW);
+}
+
+void 
+RadioEnergyModel::SetRxPowerW (double rxPowerW)
+{
+  DoSetRxPowerW (rxPowerW);
+}
+
+void 
+RadioEnergyModel::SetIdlePowerW (double idlePowerW)
+{
+  DoSetIdlePowerW (idlePowerW);
+}
+
+void 
+RadioEnergyModel::SetSleepPowerW (double sleepPowerW)
+{
+  DoSetSleepPowerW (sleepPowerW);
+}
+
+void
+RadioEnergyModel::UpdateRemainingEnergy (const RadioState destState)
+{
+  DoUpdateRemainingEnergy (destState);
+}
+
+} // namespace ns3
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/model/radio-energy-model.h	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,186 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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: Sidharth Nabar <snabar@uw.edu>, He Wu <mdzz@u.washington.edu>
+ */
+
+#ifndef RADIO_ENERGY_MODEL_H
+#define RADIO_ENERGY_MODEL_H
+
+#include "device-energy-model.h"
+
+namespace ns3 {
+
+/**
+ * \brief Keep track of energy consumption at a radio of a node.
+ *
+ * Assumption is that the radio is responsible for a significantly higher 
+ * percentage of energy consumption than the computation at the node. 
+ *
+ * The units used are: Joules (J) for energy, Watts (W) for power.
+ *
+ * This is a base class, which should be inherited and implemented by children
+ * classes.
+ */
+class RadioEnergyModel : public DeviceEnergyModel
+{
+public:
+  /**
+   * The states of the PHY layer.
+   */
+  enum RadioState
+  {
+    /**
+     * The radio is transmitting.
+     */
+    TX = 0,
+    /**
+     * The radio is receiving.
+     */
+    RX,
+    /**
+     * The radio is idle.
+     */
+    IDLE,
+    /**
+     * The radio is in sleep mode.
+     */
+    SLEEP
+  };
+
+public:
+  static TypeId GetTypeId (void);
+  RadioEnergyModel ();
+  virtual ~RadioEnergyModel ();
+
+  /**
+   * \returns the radio TX power in W.
+   */
+  double GetTxPowerW (void) const;
+
+  /**
+   * \param txPowerW the radio TX power in W
+   */
+  void SetTxPowerW (double txPowerW);
+
+  /**
+   * \returns the radio Rx power in W
+   */
+  double GetRxPowerW (void) const;
+
+  /**
+   * \param rxPowerW the radio RX power in W
+   */
+  void SetRxPowerW (double rxPowerW);
+
+  /**
+   * \returns the radio IDLE power in W
+   */
+  double GetIdlePowerW (void) const;
+
+  /**
+   * \param idlePowerW the radio IDLE power in W
+   */
+  void SetIdlePowerW (double idlePowerW);
+
+  /**
+   * \returns the radio SLEEP power in W
+   */
+  double GetSleepPowerW (void) const;
+
+  /**
+   * \param sleepPowerW the radio SLEEP power in W.
+   */
+  void SetSleepPowerW (double sleepPowerW);
+
+  /**
+   * \param destState Radio state to switch to.
+   *
+   * This function will update the remaining energy. Its implementation will be
+   * completed in child classes.
+   */
+  void UpdateRemainingEnergy (const RadioState destState);
+
+
+private:
+  /**
+   * \returns the radio TX power in W.
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual double DoGetTxPowerW (void) const = 0;
+
+  /**
+   * \param the radio TX power in W
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual void DoSetTxPowerW (double txPowerW) = 0;
+
+  /**
+   * \returns the radio RX power in W
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual double DoGetRxPowerW (void) const = 0;
+
+  /**
+   * \param the radio RX power in W
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual void DoSetRxPowerW (double rxPowerW) = 0;
+
+  /**
+   * \returns the radio IDLE power in W
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual double DoGetIdlePowerW (void) const = 0;
+
+  /**
+   * \param idlePowerW the radio IDLE power in W
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual void DoSetIdlePowerW (double idlePowerW) = 0;
+
+  /**
+   * \returns the radio SLEEP power in W
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual double DoGetSleepPowerW (void) const = 0;
+
+  /**
+   * \param sleepPowerW the radio SLEEP power in W
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual void DoSetSleepPowerW (double sleepPowerW) = 0;
+
+  /**
+   * \param destState Radio state to switch to.
+   *
+   * Concrete subclasses of this base class must implement this method.
+   */
+  virtual void DoUpdateRemainingEnergy (const RadioState destState) = 0;
+};
+
+}; // namespace ns3
+
+#endif /* RADIO_ENERGY_MODEL_H */
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/test/basic-energy-model-test.cc	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,358 @@
+/* -*-  Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
+/*
+ * Copyright (c) 2010 Network Security Lab, University of Washington, Seattle.
+ *
+ * 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
+ *
+ * Authors: He Wu <mdzz@u.washington.edu>
+ */
+
+#include "ns3/basic-energy-source.h"
+#include "ns3/basic-radio-energy-model.h"
+#include "ns3/basic-energy-source-helper.h"
+#include "ns3/basic-radio-energy-model-helper.h"
+#include "ns3/log.h"
+#include "ns3/test.h"
+#include "ns3/node.h"
+#include "ns3/simulator.h"
+#include "ns3/double.h"
+#include <math.h>
+
+using namespace ns3;
+
+NS_LOG_COMPONENT_DEFINE ("BasicEnergyModelTestSuite");
+
+/**
+ * Test case of update remaining energy for BasicEnergySource and
+ * BasicRadioEnergyModel.
+ */
+class BasicEnergyUpdateTest : public TestCase
+{
+public:
+  BasicEnergyUpdateTest ();
+  virtual ~BasicEnergyUpdateTest ();
+
+private:
+  bool DoRun (void);
+
+  /**
+   * \param state Radio state to switch to.
+   * \return False if no error occurs.
+   *
+   * Runs simulation for a while, check if final state & remaining energy is
+   * correctly updated.
+   */
+  bool StateSwitchTest (RadioEnergyModel::RadioState state);
+
+private:
+  double m_timeS;     // in seconds
+  double m_tolerance; // tolerance for power estimation
+
+  ObjectFactory m_energySource;
+  ObjectFactory m_deviceEnergyModel;
+};
+
+BasicEnergyUpdateTest::BasicEnergyUpdateTest ()
+  : TestCase ("Basic energy model update remaining energy test case")
+{
+  m_timeS = 15.5; // idle for 15 seconds before changing state
+  m_tolerance = 1.0e-13;  //
+}
+
+BasicEnergyUpdateTest::~BasicEnergyUpdateTest ()
+{
+}
+
+bool
+BasicEnergyUpdateTest::DoRun (void)
+{
+  // set types
+  m_energySource.SetTypeId ("ns3::BasicEnergySource");
+  m_deviceEnergyModel.SetTypeId ("ns3::BasicRadioEnergyModel");
+
+  // run state switch tests
+  if (StateSwitchTest (RadioEnergyModel::TX))
+    {
+      return true;
+    }
+  if (StateSwitchTest (RadioEnergyModel::RX))
+    {
+      return true;
+    }
+  if (StateSwitchTest (RadioEnergyModel::IDLE))
+    {
+      return true;
+    }
+  if (StateSwitchTest (RadioEnergyModel::SLEEP))
+    {
+      return true;
+    }
+
+  // error free
+  return false;
+}
+
+bool
+BasicEnergyUpdateTest::StateSwitchTest (
+  RadioEnergyModel::RadioState state)
+{
+  // create node
+  Ptr<Node> node = CreateObject<Node> ();
+
+  // create energy source
+  Ptr<EnergySource> source = m_energySource.Create<EnergySource> ();
+  // aggregate energy source to node
+  node->AggregateObject (source);
+
+  // create device energy model
+  Ptr<BasicRadioEnergyModel> model =
+    m_deviceEnergyModel.Create<BasicRadioEnergyModel> ();
+  // set energy source pointer
+  model->SetEnergySource (source);
+  // add device energy model to model list in energy source
+  source->AppendDeviceEnergyModel (model);
+
+  // retrieve device energy model from energy source
+  EnergySource::DeviceEnergyModelList modelList =
+    source->FindDeviceEnergyModels ("ns3::BasicRadioEnergyModel");
+  // check list
+  NS_TEST_ASSERT_MSG_EQ (false, modelList.empty (), "Model list is empty!");
+  // get pointer
+  Ptr<BasicRadioEnergyModel> devModel =
+    DynamicCast<BasicRadioEnergyModel> (modelList[0]);
+  // check pointer
+  NS_TEST_ASSERT_MSG_NE (NULL, devModel, "NULL pointer to device model!");
+
+  // schedule change of state
+  Simulator::Schedule (Seconds (m_timeS),
+                       &BasicRadioEnergyModel::UpdateRemainingEnergy, devModel, state);
+
+  // run simulation
+  Simulator::Stop (Seconds (m_timeS * 2));  // run twice as long
+  Simulator::Run ();
+  Simulator::Destroy ();
+
+  // calculate estimated remaining energy
+  double estRemainingEnergy = source->GetInitialEnergy ();
+  estRemainingEnergy -= devModel->GetIdlePowerW () * m_timeS;
+  /*
+   * Energy is updated periodically, hence we have to take into account of the
+   * update interval.
+   */
+  double actualTime = m_timeS;
+  actualTime /= devModel->GetEnergyUpdateInterval ().GetSeconds ();
+  actualTime = floor (actualTime); // rounding for update interval
+  actualTime *= devModel->GetEnergyUpdateInterval ().GetSeconds ();
+  switch (state)
+    {
+    case RadioEnergyModel::TX:
+      estRemainingEnergy -= devModel->GetTxPowerW () * actualTime;
+      break;
+    case RadioEnergyModel::RX:
+      estRemainingEnergy -= devModel->GetRxPowerW () * actualTime;
+      break;
+    case RadioEnergyModel::IDLE:
+      estRemainingEnergy -= devModel->GetIdlePowerW () * actualTime;
+      break;
+    case RadioEnergyModel::SLEEP:
+      estRemainingEnergy -= devModel->GetSleepPowerW () * actualTime;
+      break;
+    default:
+      break;
+    }
+  // obtain remaining energy
+  double remainingEnergy = source->GetRemainingEnergy ();
+  NS_LOG_UNCOND ("Remaining energy is " << remainingEnergy << "\n"
+                                        << "Estimated remaining energy is " << estRemainingEnergy << "\n"
+                                        << "Difference is " << estRemainingEnergy - remainingEnergy);
+  // check remaining energy
+  NS_TEST_ASSERT_MSG_EQ_TOL (remainingEnergy, estRemainingEnergy, m_tolerance,
+                             "Incorrect remaining energy!");
+
+
+  // obtain radio state
+  RadioEnergyModel::RadioState endState = devModel->GetCurrentState ();
+  NS_LOG_UNCOND ("Radio state is " << endState);
+  // check end state
+  NS_TEST_ASSERT_MSG_EQ (endState, state,  "Incorrect end state!");
+
+  return false; // no error
+}
+
+// ----------------------------------------------------------------------------//
+
+/**
+ * Test case of energy depletion handling for BasicEnergySource and
+ * BasicRadioEnergyModel.
+ */
+class BasicEnergyDepletionTest : public TestCase
+{
+public:
+  BasicEnergyDepletionTest ();
+  virtual ~BasicEnergyDepletionTest ();
+
+private:
+  bool DoRun (void);
+
+  // / Callback invoked when energy is drained from source.
+  void DepletionHandler (void);
+
+  /**
+   * \param simTimeS Simulation time, in seconds.
+   * \param updateIntervalS Device model update interval, in seconds.
+   * \return False if all is good.
+   *
+   * Runs simulation with specified simulation time and update interval.
+   */
+  bool DepletionTestCase (double simTimeS, double updateIntervalS);
+
+private:
+  int m_numOfModels;        // number of BasicRadioEnergyModel to install
+  int m_callbackCount;      // counter for # of callbacks invoked
+  double m_simTimeS;        // maximum simulation time, in seconds
+  double m_timeStepS;       // simulation time step size, in seconds
+  double m_updateIntervalS; // update interval of each device model
+
+};
+
+BasicEnergyDepletionTest::BasicEnergyDepletionTest ()
+  : TestCase ("Basic energy model energy depletion test case")
+{
+  m_numOfModels = 10;
+  m_callbackCount = 0;
+  m_simTimeS = 4.5;
+  m_timeStepS = 0.5;
+  m_updateIntervalS = 1.5;
+}
+
+BasicEnergyDepletionTest::~BasicEnergyDepletionTest ()
+{
+}
+
+bool
+BasicEnergyDepletionTest::DoRun (void)
+{
+  /*
+   * Run simulation with different simulation time and update interval.
+   */
+  for (double simTimeS = 0.0; simTimeS <= m_simTimeS; simTimeS += m_timeStepS)
+    {
+      for (double updateIntervalS = 0.5; updateIntervalS <= m_updateIntervalS;
+           updateIntervalS += m_timeStepS)
+        {
+          if (DepletionTestCase (simTimeS, updateIntervalS))
+            {
+              return true;
+            }
+          // reset callback count
+          m_callbackCount = 0;
+        }
+    }
+  // error free
+  return false;
+}
+
+void
+BasicEnergyDepletionTest::DepletionHandler (void)
+{
+  m_callbackCount++;
+}
+
+bool
+BasicEnergyDepletionTest::DepletionTestCase (double simTimeS,
+                                             double updateIntervalS)
+{
+  // create node
+  Ptr<Node> node = CreateObject<Node> ();
+
+  /*
+   * Create and install energy source and a single basic radio energy model on
+   * the node using helpers.
+   */
+  // source helper
+  BasicEnergySourceHelper basicSourceHelper;
+  // set energy to 0 so that we deplete energy at the beginning of simulation
+  basicSourceHelper.Set ("BasicEnergySourceInitialEnergyJ", DoubleValue (0.0));
+  // device energy model helper
+  BasicRadioEnergyModelHelper radioEnergyHelper;
+  // set update interval
+  Time updateInterval = Seconds (1.0);
+  radioEnergyHelper.Set ("PeriodicEnergyUpdateInterval",
+                         TimeValue (Seconds (updateIntervalS)));
+  // set energy depletion callback
+  BasicRadioEnergyModel::BasicEnergyDepletionCallback callback =
+    MakeCallback (&BasicEnergyDepletionTest::DepletionHandler, this);
+  radioEnergyHelper.SetDepletionCallback (callback);
+  // energy model helper
+  EnergyModelHelper energyHelper;
+  // install on node
+  energyHelper.Install (basicSourceHelper, radioEnergyHelper, node);
+
+  // Install more basic radio energy models onto the same node, using helper
+  for (int i = 1; i < m_numOfModels; i++)
+    {
+      radioEnergyHelper.Install (node);
+    }
+
+  // run simulation
+  Simulator::Stop (Seconds (simTimeS));
+  Simulator::Run ();
+  Simulator::Destroy ();
+
+  /*
+   * Calculate total number of callbacks invoked. Taking the ceiling instead of
+   * the floor here because initial update is at time = 0.
+   */
+  double tmp = ceil (simTimeS / updateIntervalS);
+  int numOfUpdates = (tmp == 0) ? 1 : tmp;
+  /*
+   * Every update will trigger *all* DeviceEnergyModels to react, therefore the
+   * total count should be numOfUpdates * m_numOfModels ^ 2
+   */
+  int totalCallbackCount = numOfUpdates * m_numOfModels * m_numOfModels;
+
+  NS_LOG_UNCOND ("Simulation time = " << simTimeS << "s\n"
+                                      << "Update interval = " << updateIntervalS << "s\n"
+                                      << "Calculated callback count is " << totalCallbackCount << "\n"
+                                      << "Actual callback count is " << m_callbackCount);
+
+  // check result
+  NS_TEST_ASSERT_MSG_EQ (totalCallbackCount, m_callbackCount,
+                         "Not all callbacks are invoked!");
+
+  return false;
+}
+
+// ----------------------------------------------------------------------------//
+
+/**
+ * Unit test suite for energy model. Although the test suite involves 2 modules
+ * it is still considered a unit test. Because a DeviceEnergyModel cannot live
+ * without an EnergySource.
+ */
+class BasicEnergyModelTestSuite : public TestSuite
+{
+public:
+  BasicEnergyModelTestSuite ();
+};
+
+BasicEnergyModelTestSuite::BasicEnergyModelTestSuite ()
+  : TestSuite ("devices-basic-energy-model", UNIT)
+{
+  AddTestCase (new BasicEnergyUpdateTest);
+  AddTestCase (new BasicEnergyDepletionTest);
+}
+
+// create an instance of the test suite
+BasicEnergyModelTestSuite g_energyModelTestSuite;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/contrib/energy/wscript	Wed Jul 07 21:54:32 2010 -0700
@@ -0,0 +1,28 @@
+## -*- Mode: python; py-indent-offset: 4; indent-tabs-mode: nil; coding: utf-8; -*-
+
+def build(bld):
+    obj = bld.create_ns3_module('energy', ['node'])
+    obj.source = [
+        'model/radio-energy-model.cc',
+        'model/basic-radio-energy-model.cc',
+        'model/energy-source.cc',
+        'model/basic-energy-source.cc',
+        'model/device-energy-model.cc',
+        'helper/energy-model-helper.cc',
+        'helper/basic-energy-source-helper.cc',
+        'helper/basic-radio-energy-model-helper.cc',
+        'test/basic-energy-model-test.cc',
+        ]
+    headers = bld.new_task_gen('ns3header')
+    headers.module = 'energy'
+    headers.source = [
+        'model/radio-energy-model.h',
+        'model/basic-radio-energy-model.h',
+        'model/energy-source.h',
+        'model/basic-energy-source.h',
+        'model/device-energy-model.h',
+        'helper/energy-model-helper.h',
+        'helper/basic-energy-source-helper.h',
+        'helper/basic-radio-energy-model-helper.h',
+        ]
+
--- a/src/wscript	Wed Jul 07 23:58:40 2010 +0900
+++ b/src/wscript	Wed Jul 07 21:54:32 2010 -0700
@@ -60,6 +60,7 @@
     'devices/wimax',
     'mpi',
     'contrib/topology-read',
+    'contrib/energy',
     )
 
 def set_options(opt):