A Discrete-Event Network Simulator
API
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
attribute-iterator.cc
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * This program is free software; you can redistribute it and/or modify
4  * it under the terms of the GNU General Public License version 2 as
5  * published by the Free Software Foundation;
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software
14  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
15  *
16  * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
17  */
18 
19 #include "attribute-iterator.h"
20 #include "ns3/config.h"
21 #include "ns3/log.h"
22 #include "ns3/pointer.h"
23 #include "ns3/object-ptr-container.h"
24 #include "ns3/string.h"
25 #include <fstream>
26 
27 
28 NS_LOG_COMPONENT_DEFINE ("AttributeIterator");
29 
30 namespace ns3 {
31 
32 
33 AttributeIterator::AttributeIterator ()
34 {
35 }
36 
37 AttributeIterator::~AttributeIterator ()
38 {
39 }
40 
41 void
42 AttributeIterator::Iterate (void)
43 {
44  for (uint32_t i = 0; i < Config::GetRootNamespaceObjectN (); ++i)
45  {
46  Ptr<Object> object = Config::GetRootNamespaceObject (i);
47  StartVisitObject (object);
48  DoIterate (object);
49  EndVisitObject ();
50  }
51  NS_ASSERT (m_currentPath.empty ());
52  NS_ASSERT (m_examined.empty ());
53 }
54 
55 bool
56 AttributeIterator::IsExamined (Ptr<const Object> object)
57 {
58  for (uint32_t i = 0; i < m_examined.size (); ++i)
59  {
60  if (object == m_examined[i])
61  {
62  return true;
63  }
64  }
65  return false;
66 }
67 
68 
69 std::string
70 AttributeIterator::GetCurrentPath (std::string attr) const
71 {
72  std::ostringstream oss;
73  for (uint32_t i = 0; i < m_currentPath.size (); ++i)
74  {
75  oss << "/" << m_currentPath[i];
76  }
77  if (attr != "")
78  {
79  oss << "/" << attr;
80  }
81  return oss.str ();
82 }
83 
84 std::string
85 AttributeIterator::GetCurrentPath (void) const
86 {
87  std::ostringstream oss;
88  for (uint32_t i = 0; i < m_currentPath.size (); ++i)
89  {
90  oss << "/" << m_currentPath[i];
91  }
92  return oss.str ();
93 }
94 
95 void
96 AttributeIterator::DoStartVisitObject (Ptr<Object> object)
97 {
98 }
99 void
100 AttributeIterator::DoEndVisitObject (void)
101 {
102 }
103 void
104 AttributeIterator::DoStartVisitPointerAttribute (Ptr<Object> object, std::string name, Ptr<Object> item)
105 {
106 }
107 void
108 AttributeIterator::DoEndVisitPointerAttribute (void)
109 {
110 }
111 void
112 AttributeIterator::DoStartVisitArrayAttribute (Ptr<Object> object, std::string name, const ObjectPtrContainerValue &vector)
113 {
114 }
115 void
116 AttributeIterator::DoEndVisitArrayAttribute (void)
117 {
118 }
119 void
120 AttributeIterator::DoStartVisitArrayItem (const ObjectPtrContainerValue &vector, uint32_t index, Ptr<Object> item)
121 {
122 }
123 void
124 AttributeIterator::DoEndVisitArrayItem (void)
125 {
126 }
127 
128 void
129 AttributeIterator::VisitAttribute (Ptr<Object> object, std::string name)
130 {
131  m_currentPath.push_back (name);
132  DoVisitAttribute (object, name);
133  m_currentPath.pop_back ();
134 }
135 
136 void
137 AttributeIterator::StartVisitObject (Ptr<Object> object)
138 {
139  m_currentPath.push_back ("$" + object->GetInstanceTypeId ().GetName ());
140  DoStartVisitObject (object);
141 }
142 void
143 AttributeIterator::EndVisitObject (void)
144 {
145  m_currentPath.pop_back ();
146  DoEndVisitObject ();
147 }
148 void
149 AttributeIterator::StartVisitPointerAttribute (Ptr<Object> object, std::string name, Ptr<Object> value)
150 {
151  m_currentPath.push_back (name);
152  m_currentPath.push_back ("$" + value->GetInstanceTypeId ().GetName ());
153  DoStartVisitPointerAttribute (object, name, value);
154 }
155 void
156 AttributeIterator::EndVisitPointerAttribute (void)
157 {
158  m_currentPath.pop_back ();
159  m_currentPath.pop_back ();
160  DoEndVisitPointerAttribute ();
161 }
162 void
163 AttributeIterator::StartVisitArrayAttribute (Ptr<Object> object, std::string name, const ObjectPtrContainerValue &vector)
164 {
165  m_currentPath.push_back (name);
166  DoStartVisitArrayAttribute (object, name, vector);
167 }
168 void
169 AttributeIterator::EndVisitArrayAttribute (void)
170 {
171  m_currentPath.pop_back ();
172  DoEndVisitArrayAttribute ();
173 }
174 
175 void
176 AttributeIterator::StartVisitArrayItem (const ObjectPtrContainerValue &vector, uint32_t index, Ptr<Object> item)
177 {
178  std::ostringstream oss;
179  oss << index;
180  m_currentPath.push_back (oss.str ());
181  m_currentPath.push_back ("$" + item->GetInstanceTypeId ().GetName ());
182  DoStartVisitArrayItem (vector, index, item);
183 }
184 void
185 AttributeIterator::EndVisitArrayItem (void)
186 {
187  m_currentPath.pop_back ();
188  m_currentPath.pop_back ();
189  DoEndVisitArrayItem ();
190 }
191 
192 
193 void
194 AttributeIterator::DoIterate (Ptr<Object> object)
195 {
196  if (IsExamined (object))
197  {
198  return;
199  }
200  TypeId tid;
201  for (tid = object->GetInstanceTypeId (); tid.HasParent (); tid = tid.GetParent ())
202  {
203  NS_LOG_DEBUG ("store " << tid.GetName ());
204  for (uint32_t i = 0; i < tid.GetAttributeN (); ++i)
205  {
206  struct TypeId::AttributeInformation info = tid.GetAttribute(i);
207  const PointerChecker *ptrChecker = dynamic_cast<const PointerChecker *> (PeekPointer (info.checker));
208  if (ptrChecker != 0)
209  {
210  NS_LOG_DEBUG ("pointer attribute " << info.name);
211  PointerValue ptr;
212  object->GetAttribute (info.name, ptr);
213  Ptr<Object> tmp = ptr.Get<Object> ();
214  if (tmp != 0)
215  {
216  StartVisitPointerAttribute (object, info.name,
217  tmp);
218  m_examined.push_back (object);
219  DoIterate (tmp);
220  m_examined.pop_back ();
221  EndVisitPointerAttribute ();
222  }
223  continue;
224  }
225  // attempt to cast to an object container
226  const ObjectPtrContainerChecker *vectorChecker = dynamic_cast<const ObjectPtrContainerChecker *> (PeekPointer (info.checker));
227  if (vectorChecker != 0)
228  {
229  NS_LOG_DEBUG ("ObjectPtrContainer attribute " << info.name);
230  ObjectPtrContainerValue vector;
231  object->GetAttribute (info.name, vector);
232  StartVisitArrayAttribute (object, info.name, vector);
233  ObjectPtrContainerValue::Iterator it;
234  for (it = vector.Begin (); it != vector.End (); ++it)
235  {
236  uint32_t j = (*it).first;
237  NS_LOG_DEBUG ("ObjectPtrContainer attribute item " << j);
238  Ptr<Object> tmp = (*it).second;
239  StartVisitArrayItem (vector, j, tmp);
240  m_examined.push_back (object);
241  DoIterate (tmp);
242  m_examined.pop_back ();
243  EndVisitArrayItem ();
244  }
245  EndVisitArrayAttribute ();
246  continue;
247  }
248  if ((info.flags & TypeId::ATTR_GET) && info.accessor->HasGetter () &&
249  (info.flags & TypeId::ATTR_SET) && info.accessor->HasSetter ())
250  {
251  VisitAttribute (object, info.name);
252  }
253  else
254  {
255  NS_LOG_DEBUG ("could not store " << info.name);
256  }
257  }
258  }
259  Object::AggregateIterator iter = object->GetAggregateIterator ();
260  bool recursiveAggregate = false;
261  while (iter.HasNext ())
262  {
263  Ptr<const Object> tmp = iter.Next ();
264  if (IsExamined (tmp))
265  {
266  recursiveAggregate = true;
267  }
268  }
269  if (!recursiveAggregate)
270  {
271  iter = object->GetAggregateIterator ();
272  while (iter.HasNext ())
273  {
274  Ptr<Object> tmp = const_cast<Object *> (PeekPointer (iter.Next ()));
275  StartVisitObject (tmp);
276  m_examined.push_back (object);
277  DoIterate (tmp);
278  m_examined.pop_back ();
279  EndVisitObject ();
280  }
281  }
282 }
283 
284 
285 } // namespace ns3
#define NS_ASSERT(condition)
Definition: assert.h:64
#define NS_LOG_COMPONENT_DEFINE(name)
Definition: log.h:122
Ptr< Object > GetRootNamespaceObject(uint32_t i)
Definition: config.cc:763
#define NS_LOG_DEBUG(msg)
Definition: log.h:255
uint32_t GetRootNamespaceObjectN(void)
Definition: config.cc:757