blob: d6bbad1a433058172fb983cacf33eb99e3e9a174 [file] [log] [blame]
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -07001/* -*- Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
2/*
3 * Copyright (c) 2011 University of California, Los Angeles
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: Ilya Moiseenko <iliamo@cs.ucla.edu>
19 */
20
21#include "annotated-topology-reader.h"
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -070022
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -080023#include "ns3/nstime.h"
24#include "ns3/log.h"
25#include "ns3/assert.h"
26#include "ns3/names.h"
27#include "ns3/net-device-container.h"
28#include "ns3/point-to-point-helper.h"
29#include "ns3/point-to-point-net-device.h"
30#include "ns3/internet-stack-helper.h"
31#include "ns3/ipv4-address-helper.h"
32#include "ns3/ipv4-global-routing-helper.h"
33#include "ns3/drop-tail-queue.h"
34#include "ns3/ipv4-interface.h"
35#include "ns3/ipv4.h"
36#include "ns3/string.h"
37#include "ns3/pointer.h"
38#include "ns3/uinteger.h"
39#include "ns3/ipv4-address.h"
Alexander Afanasyev8e0d2812012-01-19 22:38:14 -080040#include "ns3/ccnx.h"
41#include "ns3/ccnx-face.h"
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -080042
43#include "ns3/constant-position-mobility-model.h"
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -080044
45#include <boost/foreach.hpp>
46#include <boost/lexical_cast.hpp>
47
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -080048#include <set>
49
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -070050using namespace std;
51
52namespace ns3
53{
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -070054
55NS_LOG_COMPONENT_DEFINE ("AnnotatedTopologyReader");
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -070056
Alexander Afanasyev011b8592011-12-21 14:45:27 -080057AnnotatedTopologyReader::AnnotatedTopologyReader (const std::string &path, double scale/*=1.0*/)
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -080058 : m_path (path)
Alexander Afanasyevae3b7c32011-12-13 13:20:06 -080059 , m_randX (0, 100.0)
60 , m_randY (0, 100.0)
Alexander Afanasyev011b8592011-12-21 14:45:27 -080061 , m_scale (scale)
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -070062{
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -080063 NS_LOG_FUNCTION (this);
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -080064
Alexander Afanasyevbdc0d982011-12-16 01:15:26 -080065 SetMobilityModel ("ns3::ConstantPositionMobilityModel");
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -070066}
67
Alexander Afanasyevae3b7c32011-12-13 13:20:06 -080068void
69AnnotatedTopologyReader::SetBoundingBox (double ulx, double uly, double lrx, double lry)
70{
71 NS_LOG_FUNCTION (this << ulx << uly << lrx << lry);
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -080072
Alexander Afanasyevae3b7c32011-12-13 13:20:06 -080073 m_randX = UniformVariable (ulx, lrx);
74 m_randY = UniformVariable (uly, lry);
75}
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -080076
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -080077void
78AnnotatedTopologyReader::SetMobilityModel (const std::string &model)
79{
80 NS_LOG_FUNCTION (this << model);
81 m_mobilityFactory.SetTypeId (model);
82}
83
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -070084AnnotatedTopologyReader::~AnnotatedTopologyReader ()
85{
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -080086 NS_LOG_FUNCTION (this);
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -070087}
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -080088
Alexander Afanasyevae3b7c32011-12-13 13:20:06 -080089Ptr<Node>
90AnnotatedTopologyReader::CreateNode (const std::string name)
91{
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -080092 return CreateNode (name, m_randX.GetValue (), m_randY.GetValue ());
Alexander Afanasyevae3b7c32011-12-13 13:20:06 -080093}
94
95Ptr<Node>
96AnnotatedTopologyReader::CreateNode (const std::string name, double posX, double posY)
97{
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -080098 NS_LOG_FUNCTION (this << name << posX << posY);
Alexander Afanasyevae3b7c32011-12-13 13:20:06 -080099 Ptr<Node> node = CreateObject<Node> ();
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -0800100 Ptr<MobilityModel> loc = DynamicCast<MobilityModel> (m_mobilityFactory.Create ());
Alexander Afanasyevae3b7c32011-12-13 13:20:06 -0800101 node->AggregateObject (loc);
102
103 loc->SetPosition (Vector (posX, posY, 0));
104
105 Names::Add (m_path, name, node);
Alexander Afanasyev5beb35a2011-12-21 16:45:13 -0800106 m_nodes.Add (node);
Alexander Afanasyevae3b7c32011-12-13 13:20:06 -0800107
108 return node;
109}
110
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -0700111NodeContainer
Alexander Afanasyev5beb35a2011-12-21 16:45:13 -0800112AnnotatedTopologyReader::GetNodes () const
113{
114 return m_nodes;
115}
116
Alexander Afanasyeve9c9d722012-01-19 16:59:30 -0800117const std::list<TopologyReader::Link>&
Ilya Moiseenkoad9e8ab2012-01-11 19:58:34 -0800118AnnotatedTopologyReader::GetLinks () const
119{
120 return m_linksList;
121}
Alexander Afanasyev5beb35a2011-12-21 16:45:13 -0800122
123NodeContainer
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -0700124AnnotatedTopologyReader::Read (void)
125{
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800126 ifstream topgen;
127 topgen.open (GetFileName ().c_str ());
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -0700128
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800129 if ( !topgen.is_open () )
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -0700130 {
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800131 NS_LOG_ERROR ("Cannot open file " << GetFileName () << " for reading");
Alexander Afanasyev5beb35a2011-12-21 16:45:13 -0800132 return m_nodes;
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -0700133 }
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800134
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800135 while (!topgen.eof ())
136 {
137 string line;
138 getline (topgen, line);
139
140 if (line == "router") break;
141 }
142
143 while (!topgen.eof ())
144 {
145 string line;
146 getline (topgen,line);
147 if (line[0] == '#') continue; // comments
148 if (line=="link") break; // stop reading nodes
149
150 istringstream lineBuffer (line);
151 string name, city;
152 double latitude, longitude;
153
154 lineBuffer >> name >> city >> latitude >> longitude;
Alexander Afanasyev5beb35a2011-12-21 16:45:13 -0800155 if (name.empty ()) continue;
156
Alexander Afanasyev011b8592011-12-21 14:45:27 -0800157 Ptr<Node> node = CreateNode (name, m_scale*longitude, -m_scale*latitude);
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800158 }
159
160 map<string, set<string> > processedLinks; // to eliminate duplications
161
162 // SeekToSection ("link");
163 while (!topgen.eof ())
164 {
165 string line;
166 getline (topgen,line);
167 if (line == "") continue;
168 if (line[0] == '#') continue; // comments
169
170 // NS_LOG_DEBUG ("Input: [" << line << "]");
171
172 istringstream lineBuffer (line);
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800173 string from, to, capacity, metric, delay, maxPackets;
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800174
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800175 lineBuffer >> from >> to >> capacity >> metric >> delay >> maxPackets;
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800176
177 if (processedLinks[to].size () != 0 &&
178 processedLinks[to].find (from) != processedLinks[to].end ())
179 {
180 continue; // duplicated link
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -0700181 }
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800182 processedLinks[from].insert (to);
183
184 Ptr<Node> fromNode = Names::Find<Node> (m_path, from);
185 NS_ASSERT (fromNode != 0);
186 Ptr<Node> toNode = Names::Find<Node> (m_path, to);
187 NS_ASSERT (fromNode != 0);
188
189 Link link (fromNode, from, toNode, to);
190
191 link.SetAttribute ("DataRate", capacity);
192 link.SetAttribute ("OSPF", metric);
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -0800193
194 if (!delay.empty ())
195 link.SetAttribute ("Delay", delay);
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800196 if (!maxPackets.empty ())
197 link.SetAttribute ("MaxPackets", maxPackets);
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800198
199 AddLink (link);
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800200 NS_LOG_DEBUG ("New link " << from << " <==> " << to << " / " << capacity << " with " << metric << " metric (" << delay << ", " << maxPackets << ")");
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -0700201 }
202
Alexander Afanasyev5beb35a2011-12-21 16:45:13 -0800203 NS_LOG_INFO ("Annotated topology created with " << m_nodes.GetN () << " nodes and " << LinksSize () << " links");
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800204 topgen.close ();
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -0700205
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800206 ApplySettings ();
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800207
Alexander Afanasyev5beb35a2011-12-21 16:45:13 -0800208 return m_nodes;
Ilya Moiseenko7dd43be2011-08-18 18:57:12 -0700209}
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -0700210
Ilya Moiseenko58d26672011-12-08 13:48:06 -0800211void
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800212AnnotatedTopologyReader::AssignIpv4Addresses (Ipv4Address base)
Ilya Moiseenko58d26672011-12-08 13:48:06 -0800213{
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800214 Ipv4AddressHelper address (base, Ipv4Mask ("/24"));
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -0700215
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800216 BOOST_FOREACH (const Link &link, m_linksList)
Ilya Moiseenko58d26672011-12-08 13:48:06 -0800217 {
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800218 address.Assign (NetDeviceContainer (link.GetFromNetDevice (),
219 link.GetToNetDevice ()));
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -0700220
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800221 base = Ipv4Address (base.Get () + 256);
222 address.SetBase (base, Ipv4Mask ("/24"));
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800223 }
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800224}
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -0700225
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800226void
227AnnotatedTopologyReader::ApplyOspfMetric ()
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800228{
Alexander Afanasyev0777f1c2011-12-12 20:22:45 -0800229 BOOST_FOREACH (const Link &link, m_linksList)
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800230 {
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -0800231 NS_LOG_DEBUG ("OSPF: " << link.GetAttribute ("OSPF"));
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800232 uint16_t metric = boost::lexical_cast<uint16_t> (link.GetAttribute ("OSPF"));
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -0700233
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800234 {
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800235 Ptr<Ipv4> ipv4 = link.GetFromNode ()->GetObject<Ipv4> ();
Alexander Afanasyev8e0d2812012-01-19 22:38:14 -0800236 if (ipv4 != 0)
237 {
238 int32_t interfaceId = ipv4->GetInterfaceForDevice (link.GetFromNetDevice ());
239 NS_ASSERT (interfaceId >= 0);
Alexander Afanasyev0777f1c2011-12-12 20:22:45 -0800240
Alexander Afanasyev8e0d2812012-01-19 22:38:14 -0800241 ipv4->SetMetric (interfaceId,metric);
242 }
243
244 Ptr<Ccnx> ccnx = link.GetFromNode ()->GetObject<Ccnx> ();
245 if (ccnx != 0)
246 {
247 Ptr<CcnxFace> face = ccnx->GetFaceByNetDevice (link.GetFromNetDevice ());
248 NS_ASSERT (face != 0);
249
250 face->SetMetric (metric);
251 }
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800252 }
Ilya Moiseenko1eff17d2011-08-17 10:55:53 -0700253
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800254 {
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800255 Ptr<Ipv4> ipv4 = link.GetToNode ()->GetObject<Ipv4> ();
Alexander Afanasyev8e0d2812012-01-19 22:38:14 -0800256 if (ipv4 != 0)
257 {
258 int32_t interfaceId = ipv4->GetInterfaceForDevice (link.GetToNetDevice ());
259 NS_ASSERT (interfaceId >= 0);
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800260
Alexander Afanasyev8e0d2812012-01-19 22:38:14 -0800261 ipv4->SetMetric (interfaceId,metric);
262 }
263
264 Ptr<Ccnx> ccnx = link.GetToNode ()->GetObject<Ccnx> ();
265 if (ccnx != 0)
266 {
267 Ptr<CcnxFace> face = ccnx->GetFaceByNetDevice (link.GetToNetDevice ());
268 NS_ASSERT (face != 0);
269
270 face->SetMetric (metric);
271 }
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800272 }
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800273 }
274}
275
276void
277AnnotatedTopologyReader::ApplySettings ()
278{
279 PointToPointHelper p2p;
Ilya Moiseenko58d26672011-12-08 13:48:06 -0800280
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800281 BOOST_FOREACH (Link &link, m_linksList)
282 {
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800283 string tmp;
284
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -0800285 if (link.GetAttributeFailSafe ("DataRate", tmp))
286 {
Alexander Afanasyev8f5a9bb2011-12-18 19:49:02 -0800287 NS_LOG_INFO ("DataRate = " + link.GetAttribute("DataRate"));
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800288 p2p.SetDeviceAttribute ("DataRate", StringValue (link.GetAttribute ("DataRate")));
Alexander Afanasyev7dbdcaf2011-12-13 21:40:37 -0800289 }
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800290
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800291 if (link.GetAttributeFailSafe ("Delay", tmp))
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800292 {
Alexander Afanasyev8f5a9bb2011-12-18 19:49:02 -0800293 NS_LOG_INFO ("Delay = " + link.GetAttribute("Delay"));
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800294 p2p.SetChannelAttribute ("Delay", StringValue (link.GetAttribute ("Delay")));
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800295 }
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800296
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800297 NetDeviceContainer nd = p2p.Install(link.GetFromNode (), link.GetToNode ());
298 link.SetNetDevices (nd.Get (0), nd.Get (1));
299
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800300 if (link.GetAttributeFailSafe ("MaxPackets", tmp))
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800301 {
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800302 NS_LOG_INFO ("MaxPackets = " + link.GetAttribute ("MaxPackets"));
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800303
Alexander Afanasyev120bf312011-12-19 01:24:47 -0800304 PointerValue txQueue;
305
306 link.GetToNetDevice ()->GetAttribute ("TxQueue", txQueue);
307 NS_ASSERT (txQueue.Get<DropTailQueue> () != 0);
308 txQueue.Get<DropTailQueue> ()->SetAttribute ("MaxPackets", StringValue (link.GetAttribute ("MaxPackets")));
309
310 link.GetFromNetDevice ()->GetAttribute ("TxQueue", txQueue);
311 NS_ASSERT (txQueue.Get<DropTailQueue> () != 0);
312 txQueue.Get<DropTailQueue> ()->SetAttribute ("MaxPackets", StringValue (link.GetAttribute ("MaxPackets")));
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800313 }
Ilya Moiseenko7e14efa2011-12-12 17:56:22 -0800314
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800315 }
Alexander Afanasyev66e6fd72011-12-12 21:34:51 -0800316}
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800317
Alexander Afanasyeved78b632012-01-25 19:26:43 -0800318void
319AnnotatedTopologyReader::SavePositions (const std::string &file) const
320{
321 ofstream os (file.c_str (), ios::trunc);
322 os << "router\n";
323
324 for (NodeContainer::Iterator node = m_nodes.Begin ();
325 node != m_nodes.End ();
326 node++)
327 {
328 std::string name = Names::FindName (*node);
329 Ptr<MobilityModel> mobility = (*node)->GetObject<MobilityModel> ();
330 Vector position = mobility->GetPosition ();
331
332 os << name << "\t" << "unknown" << "\t" << -position.y << "\t" << position.x << "\n";
333 }
334}
335
Alexander Afanasyev8633d5d2011-12-12 18:02:31 -0800336}