merge with ns-3.5

This commit is contained in:
Pavel Boyko
2009-07-05 11:42:32 +04:00
14 changed files with 240 additions and 38 deletions

View File

@@ -35,3 +35,4 @@ dfd0bc16dc991313896f351530a3dc5a25f62e15 ns-3.3-RC4
13a5b15fbe3429a6c3d00c1bccffa2c156a0603b ns-3.5-rc1
8562a42accf6f715d312c037326ec7da48095e13 ns-3.5-rc2
a600c11ff8d40a40e88c2d692acad6512dde70c8 ns-3.5-rc3
c975274c9707b1f07d94cc51f205c351122131a5 ns-3.5

View File

@@ -4,9 +4,7 @@
This file contains ns-3 release notes (most recent releases first).
All of the ns-3 documentation is accessible from the ns-3 website:
http://www.nsnam.org
including tutorials:
http://www.nsnam.org/tutorials.html
http://www.nsnam.org including tutorials: http://www.nsnam.org/tutorials.html
Release 3.5
===========
@@ -64,8 +62,8 @@ Future releases
---------------
Our next release, which is expected to happen in 2 to 4 months from now, will
feature the merging of some of our projects currently in development including
fuller IPv6 support, and some smaller features such as a new Global ARP package
and possibly a new Testing and Validation suite.
fuller IPv6 support, some smaller features such as a new Global ARP
package, and possibly a new Testing and Validation suite.
Release 3.4
===========

View File

@@ -114,6 +114,7 @@ example: @code{class ns3::Node}.
The public header file node.h has a declaration that includes
a static GetTypeId function call:
@verbatim
class Node : public Object
{
@@ -123,21 +124,72 @@ public:
@end verbatim
This is defined in the node.cc file as follows:
@verbatim
TypeId
Node::GetTypeId (void)
{
static TypeId tid = TypeId ("ns3::Node")
.SetParent<Object> ()
.AddConstructor<Node> ()
.AddAttribute ("DeviceList", "The list of devices associated to this Node.",
ObjectVectorValue (),
MakeObjectVectorAccessor (&Node::m_devices),
MakeObjectVectorChecker<NetDevice> ())
.AddAttribute ("ApplicationList", "The list of applications associated to this Node.",
ObjectVectorValue (),
MakeObjectVectorAccessor (&Node::m_applications),
MakeObjectVectorChecker<Application> ())
.AddAttribute ("Id", "The id (unique integer) of this Node.",
TypeId::ATTR_GET, // allow only getting it.
UintegerValue (0),
MakeUintegerAccessor (&Node::m_id),
MakeUintegerChecker<uint32_t> ())
;
return tid;
}
@end verbatim
Finally, when users want to create Nodes, they call:
Look at the TypeId of an ns-3 @code{Object} class as an extended form of run
time type information (RTTI). The C++ language includes simple kind of RTTI
in order to support @code{dynamic_cast} and @code{typeid} operators.
The ``@code{.SetParent<Object> ()}'' call in the declaration above is used in
conjunction with our object aggregation mechanisms to allow safe up- and
down-casing in inheritance trees during @code{GetObject}.
The ``@code{.AddConstructor<Node> ()}'' call is used in conjunction with our
abstract object factory mechanisms to allow us to construct C++ objects without
forcing a user to know the concrete class of the object she is building.
The three calls to ``@code{.AddAttribute}'' associate a given string with a
strongly typed value in the class. Notice that you must provide a help string
which may be displayed, for example, via command line processors. Each
@code{Attribute} is associated with mechanisms for accessing the underlying
member variable in the object (for example, @code{MakeUintegerAccessor} tells
the generic @code{Attribute} code how to get to the node ID above). There are
also ``Checker'' methods which are used to validate values.
When users want to create Nodes, they will usually call some form of
@code{CreateObject},
@verbatim
Ptr<Node> n = CreateObject<Node> ();
@end verbatim
or more abstractly, using an object factory, you can create a @code{Node} object
without even knowing the concrete C++ type
@verbatim
ObjectFactory factory;
const std::string typeId = "ns3::Node'';
factory.SetTypeId(typeId);
Ptr<Object> node = factory.Create <Object> ();
@end verbatim
Both of these methods result in fully initialized attributes being available
in the resulting @code{Object} instances.
We next discuss how attributes (values associated with member variables
or functions of the class) are plumbed into the above TypeId.
@@ -206,6 +258,7 @@ and some type of global default value.
In the ns-3 attribute system, these value definitions and accessor
functions are moved into the TypeId class; e.g.:
@verbatim
NS_OBJECT_ENSURE_REGISTERED (DropTailQueue);
@@ -358,11 +411,11 @@ Now, let's set it to another value (60 packets)
@subsubsection Namespace-based access
An alternative way to get at the attribute is to use the configuration
namespace. Here, this attribute resides on a known path in this
namespace; this approach is useful if one doesn't have access to
the underlying pointers and would like to configure a specific
attribute with a single statement.
An alternative way to get at the attribute is to use the configuration namespace.
Here, this attribute resides on a known path in this namespace; this approach
is useful if one doesn't have access to the underlying pointers and would like
to configure a specific attribute with a single statement.
@verbatim
Config::Set ("/NodeList/0/DeviceList/0/TxQueue/MaxPackets", UintegerValue (25));
txQueue->GetAttribute ("MaxPackets", limit);
@@ -370,9 +423,8 @@ attribute with a single statement.
limit.Get () << " packets");
@end verbatim
We could have also used wildcards to set this value for all nodes
and all net devices (which in this simple example has the same
effect as the previous Set())
We could have also used wildcards to set this value for all nodes and all net
devices (which in this simple example has the same effect as the previous Set())
@verbatim
Config::Set ("/NodeList/*/DeviceList/*/TxQueue/MaxPackets", UintegerValue (15));
txQueue->GetAttribute ("MaxPackets", limit);
@@ -380,6 +432,22 @@ effect as the previous Set())
limit.Get () << " packets");
@end verbatim
@subsubsection Object Name Service-based access
Another way to get at the attribute is to use the object name service facility.
Here, this attribute is found using a name string. This approach is useful if
one doesn't have access to the underlying pointers and it is difficult to
determine the required concrete configuration namespaced path.
@verbatim
Names::Add ("server", serverNode);
Names::Add ("server/eth0", serverDevice);
...
Config::Set ("/Names/server/eth0/TxQueue/MaxPackets", UintegerValue (25));
@end verbatim
@subsection Setting through constructors helper classes
Arbitrary combinations of attributes can be set and fetched from
@@ -438,13 +506,13 @@ Consider this variable in class TcpSocket:
Suppose that someone working with Tcp wanted to get or set the
value of that variable using the metadata system. If it were not
already provided by ns-3, the user could declare the following addition
in the metadata system (to the TypeId declaration for TcpSocket):
in the runtime metadata system (to the TypeId declaration for TcpSocket):
@verbatim
.AddParameter ("Congestion window",
.AddAttribute ("Congestion window",
"Tcp congestion window (bytes)",
Uinteger (1),
UintegerValue (1),
MakeUintegerAccessor (&TcpSocket::m_cWnd),
MakeUintegerChecker<uint16_t> ());
MakeUintegerChecker<uint16_t> ())
@end verbatim
@@ -511,21 +579,26 @@ wants to hook it in to the attribute system, there is mainly the matter
of writing
the conversions to/from strings and attribute values. Most of this can be
copy/pasted with macro-ized code. For instance, consider class
Rectangle in the @code{src/mobility/} directory:
delcaration for Rectangle in the @code{src/mobility/} directory:
One line is added to the class declaration:
@verbatim
/**
* \brief a 2d rectangle
*/
class Rectangle
{
...
...
double xMin;
double xMax;
double yMin;
double yMax;
};
@end verbatim
One macro call and two operators, are added below the class declaration:
One macro call and two operators, must be added below the class declaration
in order to turn a Rectangle into a value usable by the @code{Attribute}
system:
@verbatim
std::ostream &operator << (std::ostream &os, const Rectangle &rectangle);
@@ -534,7 +607,7 @@ std::istream &operator >> (std::istream &is, Rectangle &rectangle);
ATTRIBUTE_HELPER_HEADER (Rectangle);
@end verbatim
In the class definition, the code looks like this:
In the class definition (@code{.cc} file), the code looks like this:
@verbatim
ATTRIBUTE_HELPER_CPP (Rectangle);
@@ -568,9 +641,9 @@ of an instance of the new class.
@node ConfigStore
@section ConfigStore
@strong{Feedback requested:} This is an experimental feature of ns-3.
It is not in the main tree. If you like this feature and would like
to provide feedback on it, please email us.
@strong{Feedback requested:} This is an experimental feature of ns-3. It is
found in @code{src/contrib} and not in the main tree. If you like this feature
and would like to provide feedback on it, please email us.
Values for ns-3 attributes can be stored in an ascii text file and
loaded into a future simulation. This feature is known as the

View File

@@ -78,23 +78,33 @@ class Tunnel
bool
N0N1VirtualSend (Ptr<Packet> packet, const Address& source, const Address& dest, uint16_t protocolNumber)
N0VirtualSend (Ptr<Packet> packet, const Address& source, const Address& dest, uint16_t protocolNumber)
{
m_n3Socket->SendTo (packet, 0, InetSocketAddress (m_n3Address, 667));
NS_LOG_DEBUG ("Send to " << m_n3Address << ": " << *packet);
m_n0Socket->SendTo (packet, 0, InetSocketAddress (m_n3Address, 667));
return true;
}
bool
N1VirtualSend (Ptr<Packet> packet, const Address& source, const Address& dest, uint16_t protocolNumber)
{
NS_LOG_DEBUG ("Send to " << m_n3Address << ": " << *packet);
m_n1Socket->SendTo (packet, 0, InetSocketAddress (m_n3Address, 667));
return true;
}
bool
N3VirtualSend (Ptr<Packet> packet, const Address& source, const Address& dest, uint16_t protocolNumber)
{
if (m_rng.GetValue () < 0.25)
{
m_n0Socket->SendTo (packet, 0, InetSocketAddress (m_n0Address, 667));
NS_LOG_DEBUG ("Send to " << m_n0Address << ": " << *packet);
m_n3Socket->SendTo (packet, 0, InetSocketAddress (m_n0Address, 667));
}
else
{
m_n1Socket->SendTo (packet, 0, InetSocketAddress (m_n1Address, 667));
NS_LOG_DEBUG ("Send to " << m_n1Address << ": " << *packet);
m_n3Socket->SendTo (packet, 0, InetSocketAddress (m_n1Address, 667));
}
return true;
}
@@ -102,6 +112,7 @@ class Tunnel
void N3SocketRecv (Ptr<Socket> socket)
{
Ptr<Packet> packet = socket->Recv (65535, 0);
NS_LOG_DEBUG ("N3SocketRecv: " << *packet);
SocketAddressTag socketAddressTag;
packet->RemovePacketTag (socketAddressTag);
m_n3Tap->Receive (packet, 0x0800, m_n3Tap->GetAddress (), m_n3Tap->GetAddress (), NetDevice::PACKET_HOST);
@@ -110,6 +121,7 @@ class Tunnel
void N0SocketRecv (Ptr<Socket> socket)
{
Ptr<Packet> packet = socket->Recv (65535, 0);
NS_LOG_DEBUG ("N0SocketRecv: " << *packet);
SocketAddressTag socketAddressTag;
packet->RemovePacketTag (socketAddressTag);
m_n0Tap->Receive (packet, 0x0800, m_n0Tap->GetAddress (), m_n0Tap->GetAddress (), NetDevice::PACKET_HOST);
@@ -118,6 +130,7 @@ class Tunnel
void N1SocketRecv (Ptr<Socket> socket)
{
Ptr<Packet> packet = socket->Recv (65535, 0);
NS_LOG_DEBUG ("N1SocketRecv: " << *packet);
SocketAddressTag socketAddressTag;
packet->RemovePacketTag (socketAddressTag);
m_n1Tap->Receive (packet, 0x0800, m_n1Tap->GetAddress (), m_n1Tap->GetAddress (), NetDevice::PACKET_HOST);
@@ -144,7 +157,7 @@ public:
// n0 tap device
m_n0Tap = CreateObject<VirtualNetDevice> ();
m_n0Tap->SetAddress (Mac48Address ("11:00:01:02:03:01"));
m_n0Tap->SetSendCallback (MakeCallback (&Tunnel::N0N1VirtualSend, this));
m_n0Tap->SetSendCallback (MakeCallback (&Tunnel::N0VirtualSend, this));
n0->AddDevice (m_n0Tap);
Ptr<Ipv4> ipv4 = n0->GetObject<Ipv4> ();
uint32_t i = ipv4->AddInterface (m_n0Tap);
@@ -154,7 +167,7 @@ public:
// n1 tap device
m_n1Tap = CreateObject<VirtualNetDevice> ();
m_n1Tap->SetAddress (Mac48Address ("11:00:01:02:03:02"));
m_n1Tap->SetSendCallback (MakeCallback (&Tunnel::N0N1VirtualSend, this));
m_n1Tap->SetSendCallback (MakeCallback (&Tunnel::N1VirtualSend, this));
n1->AddDevice (m_n1Tap);
ipv4 = n1->GetObject<Ipv4> ();
i = ipv4->AddInterface (m_n1Tap);
@@ -186,6 +199,8 @@ main (int argc, char *argv[])
#if 0
LogComponentEnable ("VirtualNetDeviceExample", LOG_LEVEL_INFO);
#endif
Packet::EnablePrinting ();
// Set up some default values for the simulation. Use the
Config::SetDefault ("ns3::OnOffApplication::PacketSize", UintegerValue (210));
@@ -260,11 +275,11 @@ main (int argc, char *argv[])
Address (InetSocketAddress (Ipv4Address::GetAny (), port)));
apps = sink.Install (c.Get (3));
apps.Start (Seconds (1.0));
apps.Stop (Seconds (10.0));
//apps.Stop (Seconds (10.0));
// Create a similar flow from n3 to n1, starting at time 1.1 seconds
onoff.SetAttribute ("Remote",
AddressValue (InetSocketAddress (Ipv4Address ("11.0.0.2"), port)));
AddressValue (InetSocketAddress (Ipv4Address ("11.0.0.1"), port)));
apps = onoff.Install (c.Get (3));
apps.Start (Seconds (1.1));
apps.Stop (Seconds (10.0));
@@ -272,7 +287,7 @@ main (int argc, char *argv[])
// Create a packet sink to receive these packets
apps = sink.Install (c.Get (1));
apps.Start (Seconds (1.1));
apps.Stop (Seconds (10.0));
//apps.Stop (Seconds (10.0));
std::ofstream ascii;
ascii.open ("virtual-net-device.tr");

View File

@@ -174,6 +174,30 @@ GlobalValue::End (void)
{
return GetVector ()->end ();
}
bool
GlobalValue::GetValueByNameFailSafe (std::string name, AttributeValue &value)
{
for (GlobalValue::Iterator gvit = GlobalValue::Begin (); gvit != GlobalValue::End (); ++gvit)
{
if ((*gvit)->GetName () == name)
{
(*gvit)->GetValue (value);
return true;
}
}
return false; // not found
}
void
GlobalValue::GetValueByName (std::string name, AttributeValue &value)
{
if (! GetValueByNameFailSafe (name, value))
{
NS_FATAL_ERROR ("Could not find GlobalValue named \"" << name << "\"");
}
}
GlobalValue::Vector *
GlobalValue::GetVector (void)
{

View File

@@ -114,6 +114,30 @@ public:
* \returns an iterator which represents a pointer to the last GlobalValue registered.
*/
static Iterator End (void);
/**
* finds the GlobalValue with the given name and returns its value
*
* @param name the name of the GlobalValue to be found
* @param value where to store the value of the found GlobalValue
*
* @return true if the GlobalValue was found, false otherwise
*/
static bool GetValueByNameFailSafe (std::string name, AttributeValue &value);
/**
* finds the GlobalValue with the given name and returns its
* value. This method cannot fail, i.e., it will trigger a
* NS_FATAL_ERROR if the requested GlobalValue is not found.
*
* @param name the name of the GlobalValue to be found
* @param value where to store the value of the found GlobalValue
*
*/
static void GetValueByName (std::string name, AttributeValue &value);
private:
friend class GlobalValueTests;
static Vector *GetVector (void);

View File

@@ -1,3 +1,23 @@
/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
/*
* Copyright (c) 2008 INRIA
*
* 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: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
* Author: Gustavo Carneiro <gjc@inescporto.pt>
*/
#ifndef BRIDGE_HELPER_H
#define BRIDGE_HELPER_H
@@ -10,12 +30,42 @@ namespace ns3 {
class Node;
class AttributeValue;
/**
* \brief Add capability to bridge multiple LAN segments (IEEE 802.1D bridging)
*/
class BridgeHelper
{
public:
BridgeHelper ();
/**
* \param n1 the name of the attribute to set
* \param v1 the value of the attribute to set
*
* Set an attribute on each ns3::BridgeNetDevice created by
* BridgeHelper::Install
*/
void SetDeviceAttribute (std::string n1, const AttributeValue &v1);
/**
* This method creates an ns3::BridgeNetDevice with the attributes
* configured by BridgeHelper::SetDeviceAttribute, adds the device
* to the node, and attaches the given NetDevices as ports of the
* bridge.
*
* \param node The node to install the device in
* \param c Container of NetDevices to add as bridge ports
* \returns A containter holding the added net device.
*/
NetDeviceContainer Install (Ptr<Node> node, NetDeviceContainer c);
/**
* This method creates an ns3::BridgeNetDevice with the attributes
* configured by BridgeHelper::SetDeviceAttribute, adds the device
* to the node, and attaches the given NetDevices as ports of the
* bridge.
*
* \param nodeName The name of the node to install the device in
* \param c Container of NetDevices to add as bridge ports
* \returns A containter holding the added net device.
*/
NetDeviceContainer Install (std::string nodeName, NetDeviceContainer c);
private:
ObjectFactory m_deviceFactory;

View File

@@ -28,6 +28,9 @@ namespace ns3 {
/**
* \brief Helper class that adds ns3::Ipv4ListRouting objects
*
* This class is expected to be used in conjunction with
* ns3::InternetStackHelper::SetRoutingHelper
*/
class Ipv4ListRoutingHelper : public Ipv4RoutingHelper
{

View File

@@ -33,7 +33,7 @@ class Node;
* For each new routing protocol created as a subclass of
* ns3::Ipv4RoutingProtocol, you need to create a subclass of
* ns3::Ipv4RoutingHelper which can be used by
* ns3::InternetStackHelper::SetRoutingProtocol and
* ns3::InternetStackHelper::SetRoutingHelper and
* ns3::InternetStackHelper::Install.
*/
class Ipv4RoutingHelper

View File

@@ -33,6 +33,9 @@ namespace ns3 {
/**
* \brief Helper class that adds ns3::Ipv4StaticRouting objects
*
* This class is expected to be used in conjunction with
* ns3::InternetStackHelper::SetRoutingHelper
*/
class Ipv4StaticRoutingHelper : public Ipv4RoutingHelper
{

View File

@@ -24,6 +24,10 @@
namespace ns3 {
/**
* \brief create non-qos MAC layers for a ns3::WifiNetDevice.
* This class can create MACs of type ns3::NqapWifiMac, ns3::NqstaWifiMac, and, ns3::AdhocWifiMac
*/
class NqosWifiMacHelper : public WifiMacHelper
{
public:

View File

@@ -29,6 +29,9 @@ namespace ns3 {
/**
* \brief Helper class that adds OLSR routing to nodes.
*
* This class is expected to be used in conjunction with
* ns3::InternetStackHelper::SetRoutingHelper
*/
class OlsrHelper : public Ipv4RoutingHelper
{

View File

@@ -27,6 +27,10 @@
namespace ns3 {
/**
* \brief create qos MAC layers for a ns3::WifiNetDevice.
* This class can create MACs of type ns3::QapWifiMac, ns3::QstaWifiMac, and, ns3::QadhocWifiMac
*/
class QosWifiMacHelper : public WifiMacHelper
{
public:

View File

@@ -178,7 +178,7 @@ Ipv4Interface::SetForwarding (bool val)
void
Ipv4Interface::Send (Ptr<Packet> p, Ipv4Address dest)
{
NS_LOG_FUNCTION_NOARGS ();
NS_LOG_FUNCTION (dest << *p);
if (!IsUp())
{
return;