A Discrete-Event Network Simulator
API
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
mobility-helper.cc
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2008 INRIA
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License version 2 as
7  * published by the Free Software Foundation;
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17  *
18  * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
19  */
20 #include "ns3/mobility-helper.h"
21 #include "ns3/mobility-model.h"
22 #include "ns3/position-allocator.h"
23 #include "ns3/hierarchical-mobility-model.h"
24 #include "ns3/log.h"
25 #include "ns3/pointer.h"
26 #include "ns3/config.h"
27 #include "ns3/simulator.h"
28 #include "ns3/names.h"
29 #include "ns3/string.h"
30 #include <iostream>
31 
32 namespace ns3 {
33 
34 NS_LOG_COMPONENT_DEFINE ("MobilityHelper");
35 
37 {
38  m_position = CreateObjectWithAttributes<RandomRectanglePositionAllocator>
39  ("X", StringValue ("ns3::ConstantRandomVariable[Constant=0.0]"),
40  "Y", StringValue ("ns3::ConstantRandomVariable[Constant=0.0]"));
41  m_mobility.SetTypeId ("ns3::ConstantPositionMobilityModel");
42 }
44 {
45 }
46 void
48 {
49  m_position = allocator;
50 }
51 
52 void
54  std::string n1, const AttributeValue &v1,
55  std::string n2, const AttributeValue &v2,
56  std::string n3, const AttributeValue &v3,
57  std::string n4, const AttributeValue &v4,
58  std::string n5, const AttributeValue &v5,
59  std::string n6, const AttributeValue &v6,
60  std::string n7, const AttributeValue &v7,
61  std::string n8, const AttributeValue &v8,
62  std::string n9, const AttributeValue &v9)
63 {
64  ObjectFactory pos;
65  pos.SetTypeId (type);
66  pos.Set (n1, v1);
67  pos.Set (n2, v2);
68  pos.Set (n3, v3);
69  pos.Set (n4, v4);
70  pos.Set (n5, v5);
71  pos.Set (n6, v6);
72  pos.Set (n7, v7);
73  pos.Set (n8, v8);
74  pos.Set (n9, v9);
75  m_position = pos.Create ()->GetObject<PositionAllocator> ();
76 }
77 
78 void
80  std::string n1, const AttributeValue &v1,
81  std::string n2, const AttributeValue &v2,
82  std::string n3, const AttributeValue &v3,
83  std::string n4, const AttributeValue &v4,
84  std::string n5, const AttributeValue &v5,
85  std::string n6, const AttributeValue &v6,
86  std::string n7, const AttributeValue &v7,
87  std::string n8, const AttributeValue &v8,
88  std::string n9, const AttributeValue &v9)
89 {
90  m_mobility.SetTypeId (type);
91  m_mobility.Set (n1, v1);
92  m_mobility.Set (n2, v2);
93  m_mobility.Set (n3, v3);
94  m_mobility.Set (n4, v4);
95  m_mobility.Set (n5, v5);
96  m_mobility.Set (n6, v6);
97  m_mobility.Set (n7, v7);
98  m_mobility.Set (n8, v8);
99  m_mobility.Set (n9, v9);
100 }
101 
102 void
104 {
105  Ptr<MobilityModel> mobility = reference->GetObject<MobilityModel> ();
106  m_mobilityStack.push_back (mobility);
107 }
108 
109 void
111 {
112  Ptr<MobilityModel> mobility = Names::Find<MobilityModel> (referenceName);
113  m_mobilityStack.push_back (mobility);
114 }
115 
116 void
118 {
119  m_mobilityStack.pop_back ();
120 }
121 
122 
123 std::string
125 {
126  return m_mobility.GetTypeId ().GetName ();
127 }
128 
129 void
131 {
132  Ptr<Object> object = node;
133  Ptr<MobilityModel> model = object->GetObject<MobilityModel> ();
134  if (model == 0)
135  {
136  model = m_mobility.Create ()->GetObject<MobilityModel> ();
137  if (model == 0)
138  {
139  NS_FATAL_ERROR ("The requested mobility model is not a mobility model: \""<<
140  m_mobility.GetTypeId ().GetName ()<<"\"");
141  }
142  if (m_mobilityStack.empty ())
143  {
144  NS_LOG_DEBUG ("node="<<object<<", mob="<<model);
145  object->AggregateObject (model);
146  }
147  else
148  {
149  // we need to setup a hierarchical mobility model
150  Ptr<MobilityModel> parent = m_mobilityStack.back ();
151  Ptr<MobilityModel> hierarchical =
152  CreateObjectWithAttributes<HierarchicalMobilityModel> ("Child", PointerValue (model),
153  "Parent", PointerValue (parent));
154  object->AggregateObject (hierarchical);
155  NS_LOG_DEBUG ("node="<<object<<", mob="<<hierarchical);
156  }
157  }
158  Vector position = m_position->GetNext ();
159  model->SetPosition (position);
160 }
161 
162 void
163 MobilityHelper::Install (std::string nodeName) const
164 {
165  Ptr<Node> node = Names::Find<Node> (nodeName);
166  Install (node);
167 }
168 void
170 {
171  for (NodeContainer::Iterator i = c.Begin (); i != c.End (); ++i)
172  {
173  Install (*i);
174  }
175 }
176 
177 void
179 {
181 }
182 static double
183 DoRound (double v)
184 {
185  if (v <= 1e-4 && v >= -1e-4)
186  {
187  return 0.0;
188  }
189  else if (v <= 1e-3 && v >= 0)
190  {
191  return 1e-3;
192  }
193  else if (v >= -1e-3 && v <= 0)
194  {
195  return -1e-3;
196  }
197  else
198  {
199  return v;
200  }
201 }
202 void
204 {
205  std::ostream* os = stream->GetStream ();
206  Ptr<Node> node = mobility->GetObject<Node> ();
207  *os << "now=" << Simulator::Now ()
208  << " node=" << node->GetId ();
209  Vector pos = mobility->GetPosition ();
210  pos.x = DoRound (pos.x);
211  pos.y = DoRound (pos.y);
212  pos.z = DoRound (pos.z);
213  Vector vel = mobility->GetVelocity ();
214  vel.x = DoRound (vel.x);
215  vel.y = DoRound (vel.y);
216  vel.z = DoRound (vel.z);
217  std::streamsize saved_precision = os->precision ();
218  std::ios::fmtflags saved_flags = os->flags ();
219  os->precision (3);
220  os->setf (std::ios::fixed,std::ios::floatfield);
221  *os << " pos=" << pos.x << ":" << pos.y << ":" << pos.z
222  << " vel=" << vel.x << ":" << vel.y << ":" << vel.z
223  << std::endl;
224  os->flags (saved_flags);
225  os->precision (saved_precision);
226 }
227 
228 void
230 {
231  std::ostringstream oss;
232  oss << "/NodeList/" << nodeid << "/$ns3::MobilityModel/CourseChange";
233  Config::ConnectWithoutContext (oss.str (),
234  MakeBoundCallback (&MobilityHelper::CourseChanged, stream));
235 }
236 void
238 {
239  for (NodeContainer::Iterator i = n.Begin (); i != n.End (); ++i)
240  {
241  EnableAscii (stream, (*i)->GetId ());
242  }
243 }
244 void
246 {
248 }
249 int64_t
251 {
252  int64_t currentStream = stream;
253  Ptr<Node> node;
254  Ptr<MobilityModel> mobility;
255  for (NodeContainer::Iterator i = c.Begin (); i != c.End (); ++i)
256  {
257  node = (*i);
258  mobility = node->GetObject<MobilityModel> ();
259  if (mobility)
260  {
261  currentStream += mobility->AssignStreams (currentStream);
262  }
263  }
264  return (currentStream - stream);
265 }
266 
267 } // namespace ns3
static void EnableAscii(Ptr< OutputStreamWrapper > stream, NodeContainer n)
int64_t AssignStreams(int64_t stream)
double x
Definition: vector.h:49
TypeId GetTypeId(void) const
smart pointer class similar to boost::intrusive_ptr
Definition: ptr.h:59
hold variables of type string
Definition: string.h:19
Hold a value for an Attribute.
Definition: attribute.h:51
#define NS_LOG_COMPONENT_DEFINE(name)
Definition: log.h:122
void SetTypeId(TypeId tid)
Iterator End(void) const
Get an iterator which indicates past-the-last Node in the container.
int64_t AssignStreams(NodeContainer c, int64_t stream)
void PushReferenceMobilityModel(Ptr< Object > reference)
a 3d vector
Definition: vector.h:31
#define NS_FATAL_ERROR(msg)
fatal error handling
Definition: fatal-error.h:72
Keep track of the current position and velocity of an object.
void Install(Ptr< Node > node) const
"Layout" a single node according to the current position allocator type.
Ptr< Object > Create(void) const
static void CourseChanged(Ptr< OutputStreamWrapper > stream, Ptr< const MobilityModel > mobility)
void AggregateObject(Ptr< Object > other)
Definition: object.cc:242
static void EnableAscii(Ptr< OutputStreamWrapper > stream, uint32_t nodeid)
keep track of a set of node pointers.
hold objects of type Ptr<T>
Definition: pointer.h:33
Iterator Begin(void) const
Get an iterator which refers to the first Node in the container.
void SetMobilityModel(std::string type, std::string n1="", const AttributeValue &v1=EmptyAttributeValue(), std::string n2="", const AttributeValue &v2=EmptyAttributeValue(), std::string n3="", const AttributeValue &v3=EmptyAttributeValue(), std::string n4="", const AttributeValue &v4=EmptyAttributeValue(), std::string n5="", const AttributeValue &v5=EmptyAttributeValue(), std::string n6="", const AttributeValue &v6=EmptyAttributeValue(), std::string n7="", const AttributeValue &v7=EmptyAttributeValue(), std::string n8="", const AttributeValue &v8=EmptyAttributeValue(), std::string n9="", const AttributeValue &v9=EmptyAttributeValue())
std::string GetName(void) const
Definition: type-id.cc:518
void Set(std::string name, const AttributeValue &value)
double y
Definition: vector.h:53
static Time Now(void)
Definition: simulator.cc:179
void SetPosition(const Vector &position)
static NodeContainer GetGlobal(void)
Create a NodeContainer that contains a list of all nodes created through NodeContainer::Create() and ...
instantiate subclasses of ns3::Object.
uint32_t GetId(void) const
Definition: node.cc:105
A network Node.
Definition: node.h:56
#define NS_LOG_DEBUG(msg)
Definition: log.h:255
static void EnableAsciiAll(Ptr< OutputStreamWrapper > stream)
std::string GetMobilityModelType(void) const
void PopReferenceMobilityModel(void)
void SetPositionAllocator(Ptr< PositionAllocator > allocator)
Ptr< T > GetObject(void) const
Definition: object.h:332
void ConnectWithoutContext(std::string path, const CallbackBase &cb)
Definition: config.cc:717
std::ostream * GetStream(void)
double z
Definition: vector.h:57
Allocate a set of positions. The allocation strategy is implemented in subclasses.