--- a/doc/howtos/howtos-application.h Fri Nov 13 09:19:06 2009 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,203 +0,0 @@
-/*!
- \page application How to create a traffic generator ?
- \anchor howtos-application
-
- <b>Question:</b> How do I create a new traffic generator ?
-
- <b>Answer:</b> It is possible to instanciate \ref ns3::Packet "Packet"
- objects, schedule events, and call functions from any piece of code
- in ns-3 so, technically, there is no single answer to the question of
- how we can write a new traffic generator. However, the
- \ref ns3::Socket "Socket" API was really designed to be the single
- point of entry for traffic generators or traffic analysers and the
- \ref ns3::Application "Application" class was designed to hold
- together any number of sockets.
-
- Implementing a new traffic generator thus boils down to:
-- implementing a new subclass of the \ref ns3::Application "Application"
- base class
-- instanciate one or many sockets within that application
-- start scheduling events when \ref ns3::Application::StartApplication "StartApplication"
- is called
-- stop scheduling events when \ref ns3::Application::StopApplication "StopApplication"
- is called
-- create packets and send them over one or many sockets in each event
-
-The following "random" generator generates packets separated by a random
-delay and with a random size.
-
-\code
-class RandomGenerator : public Application
-{
-public:
- RandomGenerator ();
- void SetDelay (RandomVariable delay);
- void SetSize (RandomVariable size);
- void SetRemote (std::string socketType,
- Address remote);
-private:
- virtual void StartApplication (void);
- virtual void StopApplication (void);
- void DoGenerate (void);
-
- RandomVariable m_delay;
- RandomVariable m_size;
- Ptr<Socket> m_socket;
-};
-\endcode
-
-The socket is created in the SetRemote method:
-\code
-void
-RandomGenerator::SetRemote (std::string socketType,
- Address remote)
-{
- TypeId tid = TypeId::LookupByName (socketType);
- m_socket = Socket::CreateSocket (GetNode (), tid);
- m_socket->Bind ();
- m_socket->ShutdownRecv ();
- m_socket->Connect (remote);
-}
-\endcode
-While the the crux of the logic is located in the DoGenerate method
-which is called from within StartApplication:
-\code
-void
-RandomGenerator::DoGenerate (void)
-{
- m_next = Simulator::Schedule (Seconds (m_delay.GetValue ()),
- &RandomGenerator::DoGenerate, this);
- Ptr<Packet> p = Create<Packet> (m_size.GetIntValue ());
- m_socket->Send (p);
-}
-\endcode
-
-To make that application more integrated in ns-3, it needs an associated
-helper class:
-\code
-class RandomAppHelper
-{
-public:
- RandomAppHelper (std::string protocol, Address remote);
- void SetPacketSize (RandomVariable packetSize);
- void SetDelay (RandomVariable delay);
- ApplicationContainer Install (NodeContainer nodes);
-private:
- std::string m_protocol;
- Address m_remote;
- RandomVariable m_packetSize;
- RandomVariable m_delay;
-};
-\endcode
-
-which could be trivially implemented as:
-\code
-ApplicationContainer
-RandomAppHelper::Install (NodeContainer nodes)
-{
- ApplicationContainer applications;
- for (NodeContainer::Iterator i = nodes.Begin (); i != nodes.End (); ++i)
- {
- Ptr<RandomAppHelper> app = CreateObject<RandomAppHelper> ();
- app->SetSize (m_packetSize);
- app->SetDelay (m_delay);
- app->SetRemote (m_protocol, m_remote);
- (*i)->AddApplication (app);
- applications.Add (app);
- }
- return applications;
-}
-\endcode
-
-Despite being functional, this API is not very consistant with the style of
-the other helper classes, all of which allow you to control the parameters
-of the underlying class through attributes and not explicit setters. The
-following API thus replaces the pair SetPacketSize/SetDelay with a single
-method SetAttribute:
-\code
-class RandomAppHelper
-{
-public:
- RandomAppHelper (std::string protocol, Address remote);
- void SetAttribute (std::string name, const AttributeValue &value);
- ApplicationContainer Install (NodeContainer c);
-private:
- std::string m_protocol;
- Address m_remote;
- ObjectFactory m_factory;
-};
-\endcode
-
-And which can be used as follows:
-\code
-RandomAppHelper app = RandomAppHelper ("ns3::TcpSocketFactory",
- InetSocketAddress (Ipv4Address ("192.168.1.10"), 10));
-app.SetAttribute ("Delay", StringValue ("Constant:2.5"));
-app.SetAttribute ("Size", StringValue ("Constant:2100"));
-app.Install (nodes);
-\endcode
-
-The implementation, in this case, is not necessarily longer but its
-simplicity hides a lot of behind-the-scenes complexity:
-
-\code
-void
-RandomAppHelper::SetAttribute (std::string name, const AttributeValue &value)
-{
- m_factory.Set (name, value);
-}
-ApplicationContainer
-RandomAppHelper::Install (NodeContainer nodes)
-{
- ApplicationContainer applications;
- for (NodeContainer::Iterator i = nodes.Begin (); i != nodes.End (); ++i)
- {
- Ptr<RandomAppHelper> app = m_factory.Create<RandomAppHelper> ();
- app->SetRemote (m_socketType, m_remote);
- (*i)->AddApplication (app);
- applications.Add (app);
- }
- return applications;
-}
-\endcode
-
-The key difference between this implementation and the previous one
-is that this helper does not handle explicitely the attributes
-delay and packet size. Instead, it stores them in an
-\ref ns3::ObjectFactory "ObjectFactory" object. This, of course,
-does not work magically, and requires extra support from the
-underlying RandomGenerator class. Specifically, it requires
-that the underlying RandomGenerator defines its attributes
-in its \ref ns3::TypeId "TypeId" in a new public static method:
-
-\code
-class RandomGenerator
-{
-public:
- static TypeId GetTypeId (void);
-};
-\endcode
-
-The corresponding implementation is shown below:
-
-\code
-TypeId
-RandomGenerator::GetTypeId (void)
-{
- static TypeId tid = TypeId ("RandomGenerator")
- .SetParent<Application> ()
- .AddConstructor<RandomGenerator> ()
- .AddAttribute ("Delay", "The delay between two packets (s)",
- RandomVariableValue (ConstantVariable (1.0)),
- MakeRandomVariableAccessor (&RandomGenerator::m_delay),
- MakeRandomVariableChecker ())
- .AddAttribute ("PacketSize", "The size of each packet (bytes)",
- RandomVariableValue (ConstantVariable (2000)),
- MakeRandomVariableAccessor (&RandomGenerator::m_size),
- MakeRandomVariableChecker ())
- ;
- return tid;
-}
-\endcode
-
-*/
--- a/doc/howtos/howtos-callbacks.h Fri Nov 13 09:19:06 2009 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,38 +0,0 @@
-/*!
-\page callbacks Using ns-3 callbacks
-\anchor howtos-callbacks
-
-\section null_callbacks Null Callbacks
-
-<b>Question:</b> The API I am using calls for using a callback (in the
-function signature), but I do not
-want to provide one. Is there a way to provide a null callback?
-
-<b>Answer:</b> Use the ns3::MakeNullCallback construct:
-\code
-template<typename R>
-Callback< R, T1, T2, T3, T4, T5, T6 > ns3::MakeNullCallback (void)
-\endcode
-
-Example usage: The ns3::Socket class uses callbacks to indicate completion
-of events such as a successful TCP connect(). These callbacks are set
-in the following function:
-\code
- void Socket::SetConnectCallback (Callback<void, Ptr<Socket> > connectionSucceeded,
- Callback<void, Ptr<Socket> > connectionFailed,
- Callback<void, Ptr<Socket> > halfClose);
-
-\endcode
-But suppose you do not care about registering a callback for the
-halfClose event (but you want to register one for the
-connectionSucceeded and connectionFailed cases). In that case, you
-can pass a null callback as the third argument. You just need to
-pass a callback with the matching signature, as follows:
-\code
- localSocket->SetConnectCallback (
- MakeCallback (&ConnectionSucceededCallback),
- MakeCallback (&ConnectionFailedCallback),
- MakeNullCallback<void, Ptr<Socket> > () );
-\endcode
-
-*/
--- a/doc/howtos/howtos-net-device.h Fri Nov 13 09:19:06 2009 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,162 +0,0 @@
-/*!
- \page net-device How to create a new OSI layer 1 + 2 implementation ?
- \anchor howtos-net-device
-
- <b>Question:</b> How do I integrate a new OSI layer 1 + 2 implementation ?
-
- <b>Answer:</b> The OSI layers 1 and 2 are represented by the ns3::NetDevice
- and ns3::Channel classes. To plug transparently in ns-3, a new layer 1+2 model
- thus simply needs to provide two new subclasses of these two base classes.
-
- To make that subclassing process easy, two skeleton classes are provided in
- the src/node directory: simple-net-device.h (ns3::SimpleNetDevice) and
- simple-channel.h (ns3::SimpleChannel) implement a broadcast passthru medium
- using 48bit MAC addresses without any kind of MAC access algorithm or PHY
- layer modeling.
-
- The ns3::SimpleChannel class is really very simple: it provides
- an implementation for the ns3::Channel::GetNDevices and ns3::Channel::GetDevice
- methods defined in the Channel base class and, then defines the channel-specific
- send and add methods:
-- The Add method is used by SimpleNetDevice::SetChannel to register a new
- SimpleNetDevice with its associated channel.
-- The Send method is used by SimpleNetDevice::Send to send a packet over the
- broadcast medium and ensure that it gets delivered to all associated devices
- (except the sender).
-
-\code
-class SimpleChannel : public Channel
-{
-public:
- static TypeId GetTypeId (void);
- SimpleChannel ();
-
- void Send (Ptr<Packet> p, uint16_t protocol, Mac48Address to, Mac48Address from,
- Ptr<SimpleNetDevice> sender);
-
- void Add (Ptr<SimpleNetDevice> device);
-
- // inherited from ns3::Channel
- virtual uint32_t GetNDevices (void) const;
- virtual Ptr<NetDevice> GetDevice (uint32_t i) const;
-
-private:
- std::vector<Ptr<SimpleNetDevice> > m_devices;
-};
-\endcode
-
-The SimpleNetDevice class is also trivial since it implements no special
-MAC-layer processing:
-\code
-class SimpleNetDevice : public NetDevice
-{
-public:
- static TypeId GetTypeId (void);
- SimpleNetDevice ();
-
- void Receive (Ptr<Packet> packet, uint16_t protocol, Mac48Address to, Mac48Address from);
- void SetChannel (Ptr<SimpleChannel> channel);
- void SetAddress (Mac48Address address);
-
- // inherited from NetDevice base class.
- virtual void SetName(const std::string name);
- ...
-};
-\endcode
-
-The code below illustrates how the three model-specific methods defined above are
-implemented:
-
-\code
-void
-SimpleNetDevice::Receive (Ptr<Packet> packet, uint16_t protocol,
- Mac48Address to, Mac48Address from)
-{
- if (to == m_address || to == Mac48Address::GetBroadcast ())
- {
- m_rxCallback (this, packet, protocol, from);
- }
-}
-void
-SimpleNetDevice::SetChannel (Ptr<SimpleChannel> channel)
-{
- m_channel = channel;
- m_channel->Add (this);
-}
-void
-SimpleNetDevice::SetAddress (Mac48Address address)
-{
- m_address = address;
-}
-\endcode
-
-Building a topology with such a device is then a matter of
-instanciating a set of SimpleNetDevice objects connected on a shared
-SimpleChannel:
-\code
-NodeContainer nodes;
-nodes.Create (10);
-Ptr<SimpleChannel> channel = CreateObject<SimpleChannel> ();
-for (uint32_t i = 0; i < nodes.GetN (); ++i)
- {
- CreateSimpleDevice (nodes.Get (i), channel);
- }
-\endcode
-
-With the following CreateSimpleDevice function:
-\code
-static Ptr<SimpleNetDevice>
-CreateSimpleDevice (Ptr<Node> node, Ptr<SimpleChannel> channel)
-{
- Ptr<SimpleNetDevice> device = CreateObject<SimpleNetDevice> ();
- device->SetAddress (Mac48Address:Allocate ());
- device->SetChannel (channel);
- node->AddDevice (device);
- return device;
-}
-\endcode
-
-Of course, ultimately, you need to provide a helper class for this new device and channel
-to save each user from having to re-implement their own CreateSimpleDevice helper
-function:
-
-\code
-class SimpleHelper
-{
-public:
- NetDeviceContainer Install (NodeContainer nodes, Ptr<SimpleChannel> channel);
- NetDeviceContainer Install (NodeContainer nodes);
-};
-\endcode
-
-with the following straightforward implementation, inspired by the CreateSimpleDevice
-function defined above:
-
-\code
-NetDeviceContainer
-SimpleHelper::Install (NodeContainer nodes, Ptr<SimpleChannel> channel)
-{
- NetDeviceContainer devices;
- for (NodeContainer::Iterator i = nodes.Begin (); i != nodes.End (); ++i)
- {
- Ptr<SimpleNetDevice> dev = CreateObject<SimpleNetDevice> ();
- dev->SetAddress (Mac48Address::Allocate ());
- dev->SetChannel (channel);
- (*i)->AddDevice (dev);
- devices.Add (dev);
- }
- return devices;
-}
-NetDeviceContainer
-SimpleHelper::Install (NodeContainer nodes)
-{
- return Install (nodes, CreateObject<SimpleChannel> ());
-}
-\endcode
-
-Of course, at some point, this device helper class should also contain a couple of
-ascii and pcap tracing helper functions but, since the default SimpleNetDevice
-class we used as an example here does not report any trace event, it would
-be of little use.
-
-*/
--- a/doc/howtos/howtos-packet-header.h Fri Nov 13 09:19:06 2009 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,119 +0,0 @@
-/*!
-\page packet-header-trailer How to create a new type of protocol header or trailer
-\anchor howtos-packet-header-trailer
-
-<b>Question:</b> I want to implement a new protocol X which uses a new
-type of header Y. How do I implement and use this new header Y in ns-3 ?
-
-<b>Answer:</b> The key is to implement a new subclass of the ns3::Header
-base class to represent your protocol header:
-\code
-class YHeader : public Header
-{
-public:
- // must be implemented to become a valid new header.
- static TypeId GetTypeId (void);
- virtual TypeId GetInstanceTypeId (void) const;
- virtual uint32_t GetSerializedSize (void) const;
- virtual void Serialize (Buffer::Iterator start) const;
- virtual uint32_t Deserialize (Buffer::Iterator start);
- virtual void Print (std::ostream &os) const;
-
- // allow protocol-specific access to the header data.
- void SetData (uint32_t data);
- uint32_t GetData (void) const;
-private:
- uint32_t m_data;
-};
-\endcode
-
-Once this class is implemented, you can easily store your protocol
-header into a packet:
-\code
-Ptr<Packet> p = ...;
-YHeader yHeader;
-yHeader.SetData (0xdeadbeaf);
-// copy the header into the packet
-p->AddHeader (yHeader);
-\endcode
-and get it out of a packet:
-\code
-Ptr<Packet> p = ...;
-YHeader yHeader;
-// copy the header from the packet
-p->RemoveHeader (yHeader);
-uint32_t data = yHeader.GetData ();
-\endcode
-
-The implementation of the new header is very simple. First, you need
-to give a TypeId to your YHeader class:
-\code
-TypeId
-YHeader::GetTypeId (void)
-{
- static TypeId tid = TypeId ("YHeader")
- .SetParent<Header> ()
- .AddConstructor<YHeader> ()
- ;
- return tid;
-}
-TypeId
-YHeader::GetInstanceTypeId (void)
-{
- return GetTypeId ();
-}
-\endcode
-
-Then, you need to allow your header to serialize and deserialize itself
-to a byte buffer in its network representation. Here, our new protocol
-header contains first a 2-byte constant, and, then, the data field so,
-the total size of the header is 2+4=6 bytes.
-\code
-uint32_t
-YHeader::GetSerializedSize (void) const
-{
- return 6;
-}
-void
-YHeader::Serialize (Buffer::Iterator start) const
-{
- // The 2 byte-constant
- start.WriteU8 (0xfe);
- start.WriteU8 (0xef);
- // The data.
- start.WriteHtonU32 (m_data);
-}
-uint32_t
-YHeader::Deserialize (Buffer::Iterator start)
-{
- uint8_t tmp;
- tmp = start.ReadU8 ();
- NS_ASSERT (tmp == 0xfe);
- tmp = start.ReadU8 ();
- NS_ASSERT (tmp == 0xef);
- m_data = start.ReadNtohU32 ();
- return 6; // the number of bytes consumed.
-}
-\endcode
-
-Finally, to make sure that Packet::Print also prints the content
-of your header, just as it prints the content of the other
-headers of the system, you need to provide a Print method:
-\code
-void
-YHeader::Print (std::ostream &os) const
-{
- os << "data=" << m_data;
-}
-\endcode
-
-The code will look the same if you want to implement a trailer,
-that is, a protocol data structure which will be appended to the
-end of the packet, not its start: you need to make sure that
-you derive from the ns3::Trailer base class and that you call
-Packet::AddTrailer and Packet::RemoveTrailer. Another important
-detail is that you must make sure to rewind the iterator in your
-Serialize and Deserialize methods writing to or reading from
-the underlying buffer.
-
-*/
--- a/doc/howtos/howtos.h Fri Nov 13 09:19:06 2009 -0800
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,20 +0,0 @@
-/*!
-\page howtos ns-3 HOWTOs
-\anchor howtos-anchor
-
-This is an organized set of frequently asked questions (FAQ) and HOWTOs
-for ns-3. This complements the following wiki pages:
-
-- <a href="http://www.nsnam.org/wiki/index.php/User_FAQ">User FAQ</a>
-- <a href="http://www.nsnam.org/wiki/index.php/Developer_FAQ">Developer FAQ</a>
-
-Please consider contributing tips to either the wiki (yourself) or
-by submitting a patch to this maintained documentation.
-
-- \subpage callbacks
-- \subpage packet-header-trailer
-- \subpage net-device
-- \subpage application
-
-*/
-
--- a/doc/main.h Fri Nov 13 09:19:06 2009 -0800
+++ b/doc/main.h Fri Nov 13 09:37:52 2009 -0800
@@ -15,12 +15,12 @@
* organizes all of the public API and supporting manual text
* along the source code directory structure. This forms the
* "ns-3 manual", and it is available in HTML and PDF forms.
- * - \ref howtos-anchor "HOWTOs": A set of HOWTOs and FAQs is
- * maintained on another Doxygen "Related Page"
* - <a href="http://www.nsnam.org/docs/tutorial/tutorial.html">tutorial</a>: The ns-3 tutorial is a separate document maintained in <a href="http://www.gnu.org/software/texinfo/"> GNU Texinfo</a>.
+ * - <a href="http://www.nsnam.org/docs/manual/manual.html">Reference manual</a>: The ns-3 tutorial is a separate document maintained in <a href="http://www.gnu.org/software/texinfo/"> GNU Texinfo</a>.
+ * - <a href="http://www.nsnam.org/docs/testing/testing.html">Testing and validation manual</a>: The ns-3 tutorial is a separate document maintained in <a href="http://www.gnu.org/software/texinfo/"> GNU Texinfo</a>.
* - The <b><a href="http://www.nsnam.org/wiki/index.php/Main_Page">ns-3 wiki</a></b>
* contains additional user-contributed material. Some wiki-contributed
- * material may migrate to and overlap with the Doxygen information.
+ * material may migrate to and overlap with the Doxygen and manual information.
*
* \section install-sec Building the Documentation
*