00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "attribute-list.h"
00021 #include "string.h"
00022 #include "singleton.h"
00023
00024 namespace ns3 {
00025
00026
00027
00028
00029
00030 AttributeList::AttributeList ()
00031 {}
00032
00033 AttributeList::AttributeList (const AttributeList &o)
00034 {
00035 for (Attrs::const_iterator i = o.m_attributes.begin (); i != o.m_attributes.end (); i++)
00036 {
00037 struct Attr attr;
00038 attr.checker = i->checker;
00039 attr.value = i->value->Copy ();
00040 m_attributes.push_back (attr);
00041 }
00042 }
00043 AttributeList &
00044 AttributeList::operator = (const AttributeList &o)
00045 {
00046 Reset ();
00047 for (Attrs::const_iterator i = o.m_attributes.begin (); i != o.m_attributes.end (); i++)
00048 {
00049 struct Attr attr;
00050 attr.checker = i->checker;
00051 attr.value = i->value->Copy ();
00052 m_attributes.push_back (attr);
00053 }
00054 return *this;
00055 }
00056 AttributeList::~AttributeList ()
00057 {
00058 Reset ();
00059 }
00060
00061 void
00062 AttributeList::Set (std::string name, const AttributeValue &value)
00063 {
00064 struct TypeId::AttributeInfo info;
00065 bool ok = TypeId::LookupAttributeByFullName (name, &info);
00066 if (!ok)
00067 {
00068 NS_FATAL_ERROR ("Could not find attribute "<<name);
00069 }
00070 ok = DoSet (&info, value);
00071 if (!ok)
00072 {
00073 NS_FATAL_ERROR ("Could not set value for attribute "<<name);
00074 }
00075 }
00076 bool
00077 AttributeList::SetFailSafe (std::string name, const AttributeValue &value)
00078 {
00079 struct TypeId::AttributeInfo info;
00080 bool ok = TypeId::LookupAttributeByFullName (name, &info);
00081 if (!ok)
00082 {
00083 return false;
00084 }
00085 ok = DoSet (&info, value);
00086 return ok;
00087 }
00088 void
00089 AttributeList::SetWithTid (TypeId tid, std::string name, const AttributeValue & value)
00090 {
00091 struct TypeId::AttributeInfo info;
00092 bool ok = tid.LookupAttributeByName (name, &info);
00093 if (!ok)
00094 {
00095 NS_FATAL_ERROR ("Could not find attribute "<<tid.GetName ()<<"::"<<name);
00096 }
00097 ok = DoSet (&info, value);
00098 if (!ok)
00099 {
00100 NS_FATAL_ERROR ("Could not set value for attribute "<<tid.GetName ()<<"::"<<name);
00101 }
00102 }
00103
00104 void
00105 AttributeList::DoSetOne (Ptr<const AttributeChecker> checker, const AttributeValue &value)
00106 {
00107
00108
00109 for (Attrs::iterator k = m_attributes.begin (); k != m_attributes.end (); k++)
00110 {
00111 if (k->checker == checker)
00112 {
00113 m_attributes.erase (k);
00114 break;
00115 }
00116 }
00117
00118 struct Attr attr;
00119 attr.checker = checker;
00120 attr.value = value.Copy ();
00121 m_attributes.push_back (attr);
00122 }
00123 bool
00124 AttributeList::DoSet (struct TypeId::AttributeInfo *info, const AttributeValue &value)
00125 {
00126 if (info->checker == 0)
00127 {
00128 return false;
00129 }
00130 bool ok = info->checker->Check (value);
00131 if (ok)
00132 {
00133 DoSetOne (info->checker, value);
00134 return true;
00135 }
00136
00137
00138 const StringValue *str = dynamic_cast<const StringValue *> (&value);
00139 if (str == 0)
00140 {
00141 return false;
00142 }
00143
00144 Ptr<AttributeValue> v = info->checker->Create ();
00145 ok = v->DeserializeFromString (str->Get (), info->checker);
00146 if (!ok)
00147 {
00148 return false;
00149 }
00150 ok = info->checker->Check (*v);
00151 if (!ok)
00152 {
00153 return false;
00154 }
00155 DoSetOne (info->checker, *v);
00156 return true;
00157 }
00158 void
00159 AttributeList::Reset (void)
00160 {
00161 m_attributes.clear ();
00162 }
00163 AttributeList *
00164 AttributeList::GetGlobal (void)
00165 {
00166 return Singleton<AttributeList>::Get ();
00167 }
00168
00169 std::string
00170 AttributeList::LookupAttributeFullNameByChecker (Ptr<const AttributeChecker> checker) const
00171 {
00172 for (uint32_t i = 0; i < TypeId::GetRegisteredN (); i++)
00173 {
00174 TypeId tid = TypeId::GetRegistered (i);
00175 for (uint32_t j = 0; j < tid.GetAttributeN (); j++)
00176 {
00177 if (checker == tid.GetAttributeChecker (j))
00178 {
00179 return tid.GetAttributeFullName (j);
00180 }
00181 }
00182 }
00183 NS_FATAL_ERROR ("Could not find requested Accessor.");
00184
00185 return "";
00186 }
00187
00188 std::string
00189 AttributeList::SerializeToString (void) const
00190 {
00191 std::ostringstream oss;
00192 for (Attrs::const_iterator i = m_attributes.begin (); i != m_attributes.end ();)
00193 {
00194 std::string name = LookupAttributeFullNameByChecker (i->checker);
00195 oss << name << "=" << i->value->SerializeToString (i->checker);
00196 i++;
00197 if (i != m_attributes.end ())
00198 {
00199 oss << "|";
00200 }
00201 }
00202 return oss.str ();
00203 }
00204 bool
00205 AttributeList::DeserializeFromString (std::string str)
00206 {
00207 Reset ();
00208
00209 std::string::size_type cur;
00210 cur = 0;
00211 do {
00212 std::string::size_type equal = str.find ("=", cur);
00213 if (equal == std::string::npos)
00214 {
00215 NS_FATAL_ERROR ("Error while parsing serialized attribute: \"" << str << "\"");
00216 break;
00217 }
00218 else
00219 {
00220 std::string name = str.substr (cur, equal-cur);
00221 struct TypeId::AttributeInfo info;
00222 if (!TypeId::LookupAttributeByFullName (name, &info))
00223 {
00224 NS_FATAL_ERROR ("Error while parsing serialized attribute: name does not exist: \"" << name << "\"");
00225 break;
00226 }
00227 else
00228 {
00229 std::string::size_type next = str.find ("|", cur);
00230 std::string value;
00231 if (next == std::string::npos)
00232 {
00233 value = str.substr (equal+1, str.size () - (equal+1));
00234 cur = str.size ();
00235 }
00236 else
00237 {
00238 value = str.substr (equal+1, next - (equal+1));
00239 cur++;
00240 }
00241 Ptr<AttributeValue> val = info.checker->Create ();
00242 bool ok = val->DeserializeFromString (value, info.checker);
00243 if (!ok)
00244 {
00245 NS_FATAL_ERROR ("Error while parsing serialized attribute: value invalid: \"" << value << "\"");
00246 break;
00247 }
00248 else
00249 {
00250 DoSetOne (info.checker, *val);
00251 }
00252 }
00253 }
00254 } while (cur != str.size ());
00255
00256 return true;
00257 }
00258
00259 UnsafeAttributeList::UnsafeAttributeList ()
00260 {}
00261 UnsafeAttributeList::UnsafeAttributeList (const UnsafeAttributeList &o)
00262 {
00263 for (uint32_t i = 0; i < o.m_attributes.size (); ++i)
00264 {
00265 Set (o.m_attributes[i].first, *(o.m_attributes[i].second));
00266 }
00267 }
00268 UnsafeAttributeList &
00269 UnsafeAttributeList::operator = (const UnsafeAttributeList &o)
00270 {
00271 m_attributes.clear ();
00272 for (uint32_t i = 0; i < o.m_attributes.size (); ++i)
00273 {
00274 Set (o.m_attributes[i].first, *(o.m_attributes[i].second));
00275 }
00276 return *this;
00277 }
00278
00279 UnsafeAttributeList::~UnsafeAttributeList ()
00280 {
00281 m_attributes.clear ();
00282 }
00283 void
00284 UnsafeAttributeList::Set (std::string name, const AttributeValue ¶m)
00285 {
00286 if (name == "")
00287 {
00288 return;
00289 }
00290 for (uint32_t i = 0; i < m_attributes.size (); ++i)
00291 {
00292 if (m_attributes[i].first == name)
00293 {
00294 m_attributes[i].second = param.Copy ();
00295 return;
00296 }
00297 }
00298 m_attributes.push_back (std::make_pair (name, param.Copy ()));
00299 }
00300
00301 AttributeList
00302 UnsafeAttributeList::GetSafe (std::string tidName) const
00303 {
00304 AttributeList list;
00305 for (uint32_t i = 0; i < m_attributes.size (); ++i)
00306 {
00307 TypeId tid = TypeId::LookupByName (tidName);
00308 list.SetWithTid (tid, m_attributes[i].first, *m_attributes[i].second);
00309 }
00310 return list;
00311 }
00312
00313
00314 }