00001 #include "attribute-iterator.h"
00002 #include "ns3/config.h"
00003 #include "ns3/log.h"
00004 #include "ns3/pointer.h"
00005 #include "ns3/object-vector.h"
00006 #include "ns3/string.h"
00007 #include <fstream>
00008
00009
00010 NS_LOG_COMPONENT_DEFINE ("AttributeIterator");
00011
00012 namespace ns3 {
00013
00014
00015 AttributeIterator::AttributeIterator ()
00016 {}
00017
00018 AttributeIterator::~AttributeIterator ()
00019 {}
00020
00021 void
00022 AttributeIterator::Iterate (void)
00023 {
00024 for (uint32_t i = 0; i < Config::GetRootNamespaceObjectN (); ++i)
00025 {
00026 Ptr<Object> object = Config::GetRootNamespaceObject (i);
00027 StartVisitObject (object);
00028 DoIterate (object);
00029 EndVisitObject ();
00030 }
00031 NS_ASSERT (m_currentPath.empty ());
00032 NS_ASSERT (m_examined.empty ());
00033 }
00034
00035 bool
00036 AttributeIterator::IsExamined (Ptr<const Object> object)
00037 {
00038 for (uint32_t i = 0; i < m_examined.size (); ++i)
00039 {
00040 if (object == m_examined[i])
00041 {
00042 return true;
00043 }
00044 }
00045 return false;
00046 }
00047
00048
00049 std::string
00050 AttributeIterator::GetCurrentPath (std::string attr) const
00051 {
00052 std::ostringstream oss;
00053 for (uint32_t i = 0; i < m_currentPath.size (); ++i)
00054 {
00055 oss << "/" << m_currentPath[i];
00056 }
00057 if (attr != "")
00058 {
00059 oss << "/" << attr;
00060 }
00061 return oss.str ();
00062 }
00063
00064 std::string
00065 AttributeIterator::GetCurrentPath (void) const
00066 {
00067 std::ostringstream oss;
00068 for (uint32_t i = 0; i < m_currentPath.size (); ++i)
00069 {
00070 oss << "/" << m_currentPath[i];
00071 }
00072 return oss.str ();
00073 }
00074
00075 void
00076 AttributeIterator::DoStartVisitObject (Ptr<Object> object)
00077 {}
00078 void
00079 AttributeIterator::DoEndVisitObject (void)
00080 {}
00081 void
00082 AttributeIterator::DoStartVisitPointerAttribute (Ptr<Object> object, std::string name, Ptr<Object> item)
00083 {}
00084 void
00085 AttributeIterator::DoEndVisitPointerAttribute (void)
00086 {}
00087 void
00088 AttributeIterator::DoStartVisitArrayAttribute (Ptr<Object> object, std::string name, const ObjectVectorValue &vector)
00089 {}
00090 void
00091 AttributeIterator::DoEndVisitArrayAttribute (void)
00092 {}
00093 void
00094 AttributeIterator::DoStartVisitArrayItem (const ObjectVectorValue &vector, uint32_t index, Ptr<Object> item)
00095 {}
00096 void
00097 AttributeIterator::DoEndVisitArrayItem (void)
00098 {}
00099
00100 void
00101 AttributeIterator::VisitAttribute (Ptr<Object> object, std::string name)
00102 {
00103 m_currentPath.push_back (name);
00104 DoVisitAttribute (object, name);
00105 m_currentPath.pop_back ();
00106 }
00107
00108 void
00109 AttributeIterator::StartVisitObject (Ptr<Object> object)
00110 {
00111 m_currentPath.push_back ("$" + object->GetInstanceTypeId ().GetName ());
00112 DoStartVisitObject (object);
00113 }
00114 void
00115 AttributeIterator::EndVisitObject (void)
00116 {
00117 m_currentPath.pop_back ();
00118 DoEndVisitObject ();
00119 }
00120 void
00121 AttributeIterator::StartVisitPointerAttribute (Ptr<Object> object, std::string name, Ptr<Object> value)
00122 {
00123 m_currentPath.push_back (name);
00124 m_currentPath.push_back ("$" + value->GetInstanceTypeId ().GetName ());
00125 DoStartVisitPointerAttribute (object, name, value);
00126 }
00127 void
00128 AttributeIterator::EndVisitPointerAttribute (void)
00129 {
00130 m_currentPath.pop_back ();
00131 m_currentPath.pop_back ();
00132 DoEndVisitPointerAttribute ();
00133 }
00134 void
00135 AttributeIterator::StartVisitArrayAttribute (Ptr<Object> object, std::string name, const ObjectVectorValue &vector)
00136 {
00137 m_currentPath.push_back (name);
00138 DoStartVisitArrayAttribute (object, name, vector);
00139 }
00140 void
00141 AttributeIterator::EndVisitArrayAttribute (void)
00142 {
00143 m_currentPath.pop_back ();
00144 DoEndVisitArrayAttribute ();
00145 }
00146
00147 void
00148 AttributeIterator::StartVisitArrayItem (const ObjectVectorValue &vector, uint32_t index, Ptr<Object> item)
00149 {
00150 std::ostringstream oss;
00151 oss << index;
00152 m_currentPath.push_back (oss.str ());
00153 m_currentPath.push_back ("$" + item->GetInstanceTypeId ().GetName ());
00154 DoStartVisitArrayItem (vector, index, item);
00155 }
00156 void
00157 AttributeIterator::EndVisitArrayItem (void)
00158 {
00159 m_currentPath.pop_back ();
00160 m_currentPath.pop_back ();
00161 DoEndVisitArrayItem ();
00162 }
00163
00164
00165 void
00166 AttributeIterator::DoIterate (Ptr<Object> object)
00167 {
00168 if (IsExamined (object))
00169 {
00170 return;
00171 }
00172 TypeId tid;
00173 for (tid = object->GetInstanceTypeId (); tid.HasParent (); tid = tid.GetParent ())
00174 {
00175 NS_LOG_DEBUG ("store " << tid.GetName ());
00176 for (uint32_t i = 0; i < tid.GetAttributeN (); ++i)
00177 {
00178 Ptr<const AttributeChecker> checker = tid.GetAttributeChecker (i);
00179 const PointerChecker *ptrChecker = dynamic_cast<const PointerChecker *> (PeekPointer (checker));
00180 if (ptrChecker != 0)
00181 {
00182 NS_LOG_DEBUG ("pointer attribute " << tid.GetAttributeName (i));
00183 PointerValue ptr;
00184 object->GetAttribute (tid.GetAttributeName (i), ptr);
00185 Ptr<Object> tmp = ptr.Get<Object> ();
00186 if (tmp != 0)
00187 {
00188 StartVisitPointerAttribute (object, tid.GetAttributeName (i), tmp);
00189 m_examined.push_back (object);
00190 DoIterate (tmp);
00191 m_examined.pop_back ();
00192 EndVisitPointerAttribute ();
00193 }
00194 continue;
00195 }
00196
00197 const ObjectVectorChecker *vectorChecker = dynamic_cast<const ObjectVectorChecker *> (PeekPointer (checker));
00198 if (vectorChecker != 0)
00199 {
00200 NS_LOG_DEBUG ("vector attribute " << tid.GetAttributeName (i));
00201 ObjectVectorValue vector;
00202 object->GetAttribute (tid.GetAttributeName (i), vector);
00203 StartVisitArrayAttribute (object, tid.GetAttributeName (i), vector);
00204 for (uint32_t j = 0; j < vector.GetN (); ++j)
00205 {
00206 NS_LOG_DEBUG ("vector attribute item " << j);
00207 Ptr<Object> tmp = vector.Get (j);
00208 StartVisitArrayItem (vector, j, tmp);
00209 m_examined.push_back (object);
00210 DoIterate (tmp);
00211 m_examined.pop_back ();
00212 EndVisitArrayItem ();
00213 }
00214 EndVisitArrayAttribute ();
00215 continue;
00216 }
00217 uint32_t flags = tid.GetAttributeFlags (i);
00218 Ptr<const AttributeAccessor> accessor = tid.GetAttributeAccessor (i);
00219 if ((flags & TypeId::ATTR_GET) && accessor->HasGetter () &&
00220 (flags & TypeId::ATTR_SET) && accessor->HasSetter ())
00221 {
00222 VisitAttribute (object, tid.GetAttributeName (i));
00223 }
00224 else
00225 {
00226 NS_LOG_DEBUG ("could not store " << tid.GetAttributeName (i));
00227 }
00228 }
00229 }
00230 Object::AggregateIterator iter = object->GetAggregateIterator ();
00231 bool recursiveAggregate = false;
00232 while (iter.HasNext ())
00233 {
00234 Ptr<const Object> tmp = iter.Next ();
00235 if (IsExamined (tmp))
00236 {
00237 recursiveAggregate = true;
00238 }
00239 }
00240 if (!recursiveAggregate)
00241 {
00242 iter = object->GetAggregateIterator ();
00243 while (iter.HasNext ())
00244 {
00245 Ptr<Object> tmp = const_cast<Object *> (PeekPointer (iter.Next ()));
00246 StartVisitObject (tmp);
00247 m_examined.push_back (object);
00248 DoIterate (tmp);
00249 m_examined.pop_back ();
00250 EndVisitObject ();
00251 }
00252 }
00253 }
00254
00255 TextFileAttributeIterator::TextFileAttributeIterator (std::ostream &os)
00256 : m_os (os)
00257 {}
00258 void
00259 TextFileAttributeIterator::DoVisitAttribute (Ptr<Object> object, std::string name)
00260 {
00261 StringValue str;
00262 object->GetAttribute (name, str);
00263 m_os << GetCurrentPath () << " " << str.Get () << std::endl;
00264 }
00265
00266 void
00267 TextFileAttributeIterator::Save (void)
00268 {
00269 Iterate ();
00270 }
00271
00272
00273
00274 }