A Discrete-Event Network Simulator
API
command-line.cc
Go to the documentation of this file.
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  * Authors: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
19  */
20 
21 
22 #include "command-line.h"
23 #include "des-metrics.h"
24 #include "log.h"
25 #include "config.h"
26 #include "global-value.h"
27 #include "system-path.h"
28 #include "type-id.h"
29 #include "string.h"
30 
31 #if defined (ENABLE_BUILD_VERSION)
32 #include "version.h"
33 #endif
34 
35 #include <algorithm> // transform
36 #include <cctype> // tolower
37 #include <cstdlib> // exit, getenv
38 #include <cstring> // strlen
39 #include <iomanip> // setw, boolalpha
40 #include <set>
41 #include <sstream>
42 
43 
51 namespace {
60 std::string
61 Encode (const std::string & source)
62 {
63  std::string buffer;
64  buffer.reserve (1.1 * source.size ());
65 
66  for(size_t pos = 0; pos != source.size (); ++pos)
67  {
68  /* *NS_CHECK_STYLE_OFF* */
69  switch (source[pos])
70  {
71  case '&': buffer.append ("&amp;"); break;
72  case '\"': buffer.append ("&quot;"); break;
73  case '\'': buffer.append ("&apos;"); break;
74  // case '>': buffer.append ("&gt;"); break;
75 
76  case '<': {
77  // Special case:
78  // "...blah <file..." is not allowed
79  // "...foo<bar..." is allowed
80  if (buffer.back () == ' ')
81  {
82  buffer.append ("&lt;");
83  }
84  else
85  {
86  buffer.append ("<");
87  }
88 
89  break;
90  }
91 
92  default: buffer.append (&source[pos], 1); break;
93  }
94  /* *NS_CHECK_STYLE_ON* */
95  }
96  return buffer;
97 }
98 
99 } // anonymous namespace
100 
101 
102 namespace ns3 {
103 
104 NS_LOG_COMPONENT_DEFINE ("CommandLine");
105 
107  : m_NNonOptions (0),
108  m_nonOptionCount (0),
109  m_usage (),
110  m_shortName ()
111 {
112  NS_LOG_FUNCTION (this);
113 }
114 CommandLine::CommandLine (const std::string filename)
115  : m_NNonOptions (0),
116  m_nonOptionCount (0),
117  m_usage ()
118 {
119  NS_LOG_FUNCTION (this << filename);
120  std::string basename = SystemPath::Split (filename).back ();
121  m_shortName = basename.substr (0, basename.rfind (".cc"));
122 }
123 
125 {
126  Copy (cmd);
127 }
128 CommandLine &
130 {
131  Clear ();
132  Copy (cmd);
133  return *this;
134 }
136 {
137  NS_LOG_FUNCTION (this);
138  Clear ();
139 }
140 void
142 {
143  NS_LOG_FUNCTION (&cmd);
144 
145  std::copy (cmd.m_options.begin (), cmd.m_options.end (), m_options.end ());
146  std::copy (cmd.m_nonOptions.begin (), cmd.m_nonOptions.end (), m_nonOptions.end ());
147 
148  m_NNonOptions = cmd.m_NNonOptions;
149  m_nonOptionCount = 0;
150  m_usage = cmd.m_usage;
151  m_shortName = cmd.m_shortName;
152 }
153 void
155 {
156  NS_LOG_FUNCTION (this);
157 
158  for (auto i : m_options)
159  {
160  delete i;
161  }
162  for (auto i : m_nonOptions)
163  {
164  delete i;
165  }
166  m_options.clear ();
167  m_nonOptions.clear ();
168  m_NNonOptions = 0;
169  m_usage = "";
170  m_shortName = "";
171 }
172 
173 void
174 CommandLine::Usage (const std::string usage)
175 {
176  m_usage = usage;
177 }
178 
179 std::string
181 {
182  return m_shortName;
183 }
184 
186 {
187  NS_LOG_FUNCTION (this);
188 }
189 
190 void
191 CommandLine::Parse (std::vector<std::string> args)
192 {
193  NS_LOG_FUNCTION (this << args.size () << args);
194 
196 
197  m_nonOptionCount = 0;
198 
199  if (args.size () > 0)
200  {
201  args.erase (args.begin ()); // discard the program name
202 
203  for (const auto & param : args)
204  {
205  if (HandleOption (param))
206  {
207  continue;
208  }
209  if (HandleNonOption (param))
210  {
211  continue;
212  }
213 
214  // is this possible?
215  NS_ASSERT_MSG (false,
216  "unexpected error parsing command line parameter: '"
217  << param << "'");
218 
219  }
220  }
221 
222 #ifdef ENABLE_DES_METRICS
223  DesMetrics::Get ()->Initialize (args);
224 #endif
225 
226 }
227 
228 bool
229 CommandLine::HandleOption (const std::string & param) const
230 {
231  // remove leading "--" or "-"
232  std::string arg = param;
233  std::string::size_type cur = arg.find ("--");
234  if (cur == 0)
235  {
236  arg = arg.substr (2, arg.size () - 2);
237  }
238  else
239  {
240  cur = arg.find ("-");
241  if (cur == 0)
242  {
243  arg = arg.substr (1, arg.size () - 1);
244  }
245  else
246  {
247  // non-option argument?
248  return false;
249  }
250  }
251  // find any value following '='
252  cur = arg.find ("=");
253  std::string name, value;
254  if (cur == std::string::npos)
255  {
256  name = arg;
257  value = "";
258  }
259  else
260  {
261  name = arg.substr (0, cur);
262  value = arg.substr (cur + 1, arg.size () - (cur + 1));
263  }
264  HandleArgument (name, value);
265 
266  return true;
267 }
268 
269 bool
270 CommandLine::HandleNonOption (const std::string &value)
271 {
272  NS_LOG_FUNCTION (this << value);
273 
274  if (m_nonOptionCount == m_nonOptions.size ())
275  {
276  // Add an unspecified non-option as a string
277  NS_LOG_LOGIC ("adding StringItem, NOCount:" << m_nonOptionCount
278  << ", NOSize:" << m_nonOptions.size ());
279  StringItem * item = new StringItem;
280  item->m_name = "extra-non-option-argument";
281  item->m_help = "Extra non-option argument encountered.";
282  item->m_value = value;
283  m_nonOptions.push_back (item);
284  }
285 
286  auto i = m_nonOptions[m_nonOptionCount];
287  if (!i->Parse (value))
288  {
289  std::cerr << "Invalid non-option argument value "
290  << value << " for " << i->m_name
291  << std::endl;
292  PrintHelp (std::cerr);
293  std::exit (1);
294  }
296  return true;
297 }
298 
299 
300 
301 void
302 CommandLine::Parse (int argc, char *argv[])
303 {
304  NS_LOG_FUNCTION (this << argc);
305  std::vector<std::string> args (argv, argv + argc);
306  Parse (args);
307 }
308 
309 void
310 CommandLine::PrintHelp (std::ostream &os) const
311 {
312  NS_LOG_FUNCTION (this);
313 
314  // Hack to show just the declared non-options
315  Items nonOptions (m_nonOptions.begin (),
316  m_nonOptions.begin () + m_NNonOptions);
317  os << m_shortName
318  << (m_options.size () ? " [Program Options]" : "")
319  << (nonOptions.size () ? " [Program Arguments]" : "")
320  << " [General Arguments]"
321  << std::endl;
322 
323  if (m_usage.length ())
324  {
325  os << std::endl;
326  os << m_usage << std::endl;
327  }
328 
329  std::size_t width = 0;
330  for (auto it : m_options)
331  {
332  width = std::max (width, it->m_name.size ());
333  }
334  for (auto it : nonOptions)
335  {
336  width = std::max (width, it->m_name.size ());
337  }
338  width += 3; // room for ": " between option and help
339 
340  if (!m_options.empty ())
341  {
342  os << std::endl;
343  os << "Program Options:" << std::endl;
344  for (auto i : m_options)
345  {
346  os << " --"
347  << std::left << std::setw (width) << ( i->m_name + ":")
348  << std::right
349  << i->m_help;
350 
351  if ( i->HasDefault ())
352  {
353  os << " [" << i->GetDefault () << "]";
354  }
355  os << std::endl;
356  }
357  }
358 
359  if (!nonOptions.empty ())
360  {
361  width += 2; // account for "--" added above
362  os << std::endl;
363  os << "Program Arguments:" << std::endl;
364  for (auto i : nonOptions)
365  {
366  os << " "
367  << std::left << std::setw (width) << ( i->m_name + ":")
368  << std::right
369  << i->m_help;
370 
371  if ( i->HasDefault ())
372  {
373  os << " [" << i->GetDefault () << "]";
374  }
375  os << std::endl;
376  }
377  }
378 
379  os << std::endl;
380  os
381  << "General Arguments:\n"
382  << " --PrintGlobals: Print the list of globals.\n"
383  << " --PrintGroups: Print the list of groups.\n"
384  << " --PrintGroup=[group]: Print all TypeIds of group.\n"
385  << " --PrintTypeIds: Print all TypeIds.\n"
386  << " --PrintAttributes=[typeid]: Print all attributes of typeid.\n"
387  << " --PrintVersion: Print the ns-3 version.\n"
388  << " --PrintHelp: Print this help message.\n"
389  << std::endl;
390 }
391 
392 #include <unistd.h> // getcwd
393 std::string
395 {
396 #if defined (ENABLE_BUILD_VERSION)
397  return Version::LongVersion ();
398 #else
399  return std::string{"Build version support is not enabled, reconfigure with "
400  "--enable-build-version flag"};
401 #endif
402 }
403 
404 void
405 CommandLine::PrintVersion (std::ostream & os) const
406 {
407  os << GetVersion () << std::endl;
408 }
409 
410 void
412 {
413  NS_LOG_FUNCTION (this);
414 
415  const char * envVar = std::getenv ("NS_COMMANDLINE_INTROSPECTION");
416  if (envVar == 0 || std::strlen (envVar) == 0)
417  {
418  return;
419  }
420 
421  if (m_shortName.size () == 0)
422  {
423  NS_FATAL_ERROR ("No file name on example-to-run; forgot to use CommandLine var (__FILE__)?");
424  return;
425  }
426 
427  // Hack to show just the declared non-options
428  Items nonOptions (m_nonOptions.begin (),
429  m_nonOptions.begin () + m_NNonOptions);
430 
431  std::string outf = SystemPath::Append (std::string (envVar), m_shortName + ".command-line");
432 
433  NS_LOG_INFO ("Writing CommandLine doxy to " << outf);
434 
435  std::fstream os (outf, std::fstream::out);
436 
437  os << "/**\n \\file " << m_shortName << ".cc\n"
438  << "<h3>Usage</h3>\n"
439  << "<code>$ ./ns3 run \"" << m_shortName
440  << (m_options.size () ? " [Program Options]" : "")
441  << (nonOptions.size () ? " [Program Arguments]" : "")
442  << "\"</code>\n";
443 
444  if (m_usage.length ())
445  {
446  os << Encode (m_usage) << "\n";
447  }
448 
449  auto listOptions = [&os](Items items, std::string pre)
450  {
451  os << "<dl>\n";
452  for (const auto i : items)
453  {
454  os << " <dt>" << pre << i->m_name << " </dt>\n"
455  << " <dd>" << Encode (i->m_help);
456 
457  if ( i->HasDefault ())
458  {
459  os << " [" << Encode (i->GetDefault ()) << "]";
460  }
461  os << " </dd>\n";
462  }
463  os << "</dl>\n";
464  };
465 
466  if (!m_options.empty ())
467  {
468  os << std::endl;
469  os << "<h3>Program Options</h3>\n";
470  listOptions (m_options, "\\c --");
471  }
472 
473  if (!nonOptions.empty ())
474  {
475  os << std::endl;
476  os << "<h3>Program Arguments</h3>\n";
477  listOptions (nonOptions, "\\c ");
478  }
479 
480  os << "*/" << std::endl;
481 
482  // All done, don't need to actually run the example
483  os.close ();
484  std::exit (0);
485 }
486 
487 void
488 CommandLine::PrintGlobals (std::ostream &os) const
489 {
490  NS_LOG_FUNCTION (this);
491 
492  os << "Global values:" << std::endl;
493 
494  // Sort output
495  std::vector<std::string> globals;
496 
497  for (auto i = GlobalValue::Begin(); i != GlobalValue::End(); ++i)
498  {
499  std::stringstream ss;
500  ss << " --" << (*i)->GetName () << "=[";
501  Ptr<const AttributeChecker> checker = (*i)->GetChecker ();
502  StringValue v;
503  (*i)->GetValue (v);
504  ss << v.Get () << "]" << std::endl;
505  ss << " " << (*i)->GetHelp () << std::endl;
506  globals.push_back (ss.str ());
507  }
508  std::sort (globals.begin (), globals.end ());
509  for (const auto & s : globals)
510  {
511  os << s;
512  }
513 }
514 
515 void
516 CommandLine::PrintAttributeList (std::ostream &os, const TypeId tid, std::stringstream & header) const
517 {
518  NS_LOG_FUNCTION (this);
519 
520  if (!tid.GetAttributeN ())
521  {
522  return;
523  }
524  os << header.str() << "\n";
525  // To sort output
526  std::vector<std::string> attributes;
527 
528  for (uint32_t i = 0; i < tid.GetAttributeN (); ++i)
529  {
530  std::stringstream ss;
531  ss << " --" << tid.GetAttributeFullName (i) << "=[";
532  struct TypeId::AttributeInformation info = tid.GetAttribute (i);
533  ss << info.initialValue->SerializeToString (info.checker) << "]\n"
534  << " " << info.help << "\n";
535  attributes.push_back (ss.str ());
536  }
537  std::sort (attributes.begin (), attributes.end ());
538  for (const auto & s : attributes)
539  {
540  os << s;
541  }
542 }
543 
544 void
545 CommandLine::PrintAttributes (std::ostream &os, const std::string &type) const
546 {
547  NS_LOG_FUNCTION (this);
548 
549  TypeId tid;
550  if (!TypeId::LookupByNameFailSafe (type, &tid))
551  {
552  NS_FATAL_ERROR ("Unknown type=" << type << " in --PrintAttributes");
553  }
554 
555  std::stringstream header;
556  header << "Attributes for TypeId " << tid.GetName ();
557  PrintAttributeList (os, tid, header);
558  header.str("");
559 
560  //Parent Attributes
561  if (tid.GetParent () != tid)
562  {
563  TypeId tmp = tid.GetParent ();
564  while (tmp.GetParent () != tmp)
565  {
566  header << "Attributes defined in parent class " << tmp.GetName ();
567  PrintAttributeList (os, tmp, header);
568  header.str("");
569  tmp = tmp.GetParent ();
570  }
571  }
572 }
573 
574 
575 void
576 CommandLine::PrintGroup (std::ostream &os, const std::string &group) const
577 {
578  NS_LOG_FUNCTION (this);
579 
580  os << "TypeIds in group " << group << ":" << std::endl;
581 
582  // Sort output
583  std::vector<std::string> groupTypes;
584 
585  for (uint16_t i = 0; i < TypeId::GetRegisteredN (); ++i)
586  {
587  std::stringstream ss;
588  TypeId tid = TypeId::GetRegistered (i);
589  if (tid.GetGroupName () == group)
590  {
591  ss << " " << tid.GetName () << std::endl;
592  }
593  groupTypes.push_back (ss.str ());
594  }
595  std::sort (groupTypes.begin (), groupTypes.end ());
596  for (const auto & s : groupTypes)
597  {
598  os << s;
599  }
600 }
601 
602 void
603 CommandLine::PrintTypeIds (std::ostream &os) const
604 {
605  NS_LOG_FUNCTION (this);
606  os << "Registered TypeIds:" << std::endl;
607 
608  // Sort output
609  std::vector<std::string> types;
610 
611  for (uint16_t i = 0; i < TypeId::GetRegisteredN (); ++i)
612  {
613  std::stringstream ss;
614  TypeId tid = TypeId::GetRegistered (i);
615  ss << " " << tid.GetName () << std::endl;
616  types.push_back (ss.str ());
617  }
618  std::sort (types.begin (), types.end ());
619  for (const auto & s : types)
620  {
621  os << s;
622  }
623 }
624 
625 void
626 CommandLine::PrintGroups (std::ostream &os) const
627 {
628  NS_LOG_FUNCTION (this);
629 
630  std::set<std::string> groups;
631  for (uint16_t i = 0; i < TypeId::GetRegisteredN (); ++i)
632  {
633  TypeId tid = TypeId::GetRegistered (i);
634  groups.insert (tid.GetGroupName ());
635  }
636 
637  os << "Registered TypeId groups:" << std::endl;
638  // Sets are already sorted
639  for (const auto & s : groups)
640  {
641  os << " " << s << std::endl;
642  }
643 }
644 
645 void
646 CommandLine::HandleArgument (const std::string &name, const std::string &value) const
647 {
648  NS_LOG_FUNCTION (this << name << value);
649 
650  NS_LOG_DEBUG ("Handle arg name=" << name << " value=" << value);
651 
652  // Hard-coded options
653  if (name == "PrintHelp" || name == "help")
654  {
655  // method below never returns.
656  PrintHelp (std::cout);
657  std::exit (0);
658  }
659  if (name == "PrintVersion" || name == "version")
660  {
661  //Print the version, then exit the program
662  PrintVersion (std::cout);
663  std::exit (0);
664  }
665  else if (name == "PrintGroups")
666  {
667  // method below never returns.
668  PrintGroups (std::cout);
669  std::exit (0);
670  }
671  else if (name == "PrintTypeIds")
672  {
673  // method below never returns.
674  PrintTypeIds (std::cout);
675  std::exit (0);
676  }
677  else if (name == "PrintGlobals")
678  {
679  // method below never returns.
680  PrintGlobals (std::cout);
681  std::exit (0);
682  }
683  else if (name == "PrintGroup")
684  {
685  // method below never returns.
686  PrintGroup (std::cout, value);
687  std::exit (0);
688  }
689  else if (name == "PrintAttributes")
690  {
691  // method below never returns.
692  PrintAttributes (std::cout, value);
693  std::exit (0);
694  }
695  else
696  {
697  for (auto i : m_options)
698  {
699  if (i->m_name == name)
700  {
701  if (!i->Parse (value))
702  {
703  std::cerr << "Invalid argument value: "
704  << name << "=" << value << std::endl;
705  PrintHelp (std::cerr);
706  std::exit (1);
707  }
708  else
709  {
710  return;
711  }
712  }
713  }
714  }
715  // Global or ConfigPath options
716  if (!Config::SetGlobalFailSafe (name, StringValue (value))
717  && !Config::SetDefaultFailSafe (name, StringValue (value)))
718  {
719  std::cerr << "Invalid command-line arguments: --"
720  << name << "=" << value << std::endl;
721  PrintHelp (std::cerr);
722  std::exit (1);
723  }
724 }
725 
726 bool
728 {
729  return m_default != "";
730 }
731 
732 std::string
734 {
735  return m_default;
736 }
737 
738 bool
739 CommandLine::CallbackItem::Parse (const std::string value)
740 {
741  NS_LOG_FUNCTION (this);
742  NS_LOG_DEBUG ("CommandLine::CallbackItem::Parse \"" << value << "\"");
743  return m_callback (value);
744 }
745 
746 void
747 CommandLine::AddValue (const std::string &name,
748  const std::string &help,
750  std::string defaultValue /* = "" */)
751 
752 {
753  NS_LOG_FUNCTION (this << &name << &help << &callback);
754  CallbackItem *item = new CallbackItem ();
755  item->m_name = name;
756  item->m_help = help;
757  item->m_callback = callback;
758  item->m_default = defaultValue;
759  m_options.push_back (item);
760 }
761 
762 void
763 CommandLine::AddValue (const std::string &name,
764  const std::string &attributePath)
765 {
766  NS_LOG_FUNCTION (this << name << attributePath);
767  // Attribute name is last token
768  std::size_t colon = attributePath.rfind ("::");
769  const std::string typeName = attributePath.substr (0, colon);
770  NS_LOG_DEBUG ("typeName: '" << typeName << "', colon: " << colon);
771 
772  TypeId tid;
773  if (!TypeId::LookupByNameFailSafe (typeName, &tid))
774  {
775  NS_FATAL_ERROR ("Unknown type=" << typeName);
776  }
777 
778  const std::string attrName = attributePath.substr (colon + 2);
779  struct TypeId::AttributeInformation info;
780  if (!tid.LookupAttributeByName (attrName, &info))
781  {
782  NS_FATAL_ERROR ("Attribute not found: " << attributePath);
783  }
784 
785  std::stringstream ss;
786  ss << info.help
787  << " (" << attributePath << ") ["
788  << info.initialValue->SerializeToString (info.checker) << "]";
789 
790  AddValue (name, ss.str (),
792 }
793 
794 std::string
795 CommandLine::GetExtraNonOption (std::size_t i) const
796 {
797  std::string value;
798 
799  if (m_nonOptions.size () >= i + m_NNonOptions)
800  {
801  auto ip = dynamic_cast<StringItem *> (m_nonOptions[i + m_NNonOptions]);
802  if (ip != NULL)
803  {
804  value = ip->m_value;
805  }
806  }
807  return value;
808 }
809 
810 std::size_t
812 {
813  if (m_nonOptions.size () > m_NNonOptions)
814  {
815  return m_nonOptions.size () - m_NNonOptions;
816  }
817  else
818  {
819  return 0;
820  }
821 }
822 
823 
824 /* static */
825 bool
826 CommandLine::HandleAttribute (const std::string name,
827  const std::string value)
828 {
829  bool success = true;
830  if (!Config::SetGlobalFailSafe (name, StringValue (value))
831  && !Config::SetDefaultFailSafe (name, StringValue (value)))
832  {
833  success = false;
834  }
835  return success;
836 }
837 
838 
839 bool
841 {
842  return false;
843 }
844 
845 bool
846 CommandLine::StringItem::Parse (const std::string value)
847 {
848  m_value = value;
849  return true;
850 }
851 
852 bool
854 {
855  return false;
856 }
857 
858 std::string
860 {
861  return "";
862 }
863 
864 template <>
865 std::string
866 CommandLineHelper::GetDefault<bool> (const bool & val)
867 {
868  std::ostringstream oss;
869  oss << std::boolalpha << val;
870  return oss.str ();
871 }
872 
873 template <>
874 bool
875 CommandLineHelper::UserItemParse<bool> (const std::string value, bool & val)
876 {
877  std::string src = value;
878  std::transform (src.begin (), src.end (), src.begin (),
879  [](char c) {return static_cast<char> (std::tolower (c)); });
880  if (src.length () == 0)
881  {
882  val = !val;
883  return true;
884  }
885  else if ( (src == "true") || (src == "t") )
886  {
887  val = true;
888  return true;
889  }
890  else if ( (src == "false") || (src == "f") )
891  {
892  val = false;
893  return true;
894  }
895  else
896  {
897  std::istringstream iss;
898  iss.str (src);
899  iss >> val;
900  return !iss.bad () && !iss.fail ();
901  }
902 }
903 
904 template <>
905 std::string
907 {
908  std::ostringstream oss;
909  oss << val.As ();
910  return oss.str ();
911 }
912 
913 template <>
914 bool
915 CommandLineHelper::UserItemParse<uint8_t> (const std::string value, uint8_t & val)
916 {
917  uint8_t oldVal = val;
918  long newVal;
919 
920  try
921  {
922  newVal = std::stoi (value);
923  }
924  catch (std::invalid_argument & ia)
925  {
926  NS_LOG_WARN ("invalid argument: " << ia.what ());
927  val = oldVal;
928  return false;
929  }
930  catch (std::out_of_range & oor)
931  {
932  NS_LOG_WARN ("out of range: " << oor.what ());
933  val = oldVal;
934  return false;
935  }
936  if (newVal < 0 || newVal > 255)
937  {
938  return false;
939  }
940  val = newVal;
941  return true;
942 }
943 
944 
945 std::ostream &
946 operator << (std::ostream & os, const CommandLine & cmd)
947 {
948  cmd.PrintHelp (os);
949  return os;
950 }
951 
952 } // namespace ns3
#define max(a, b)
Definition: 80211b.c:43
An argument Item using a Callback to parse the input.
Definition: command-line.h:485
std::string GetDefault(void) const
ns3::Callback< bool, std::string > m_callback
The Callback.
Definition: command-line.h:498
virtual bool Parse(const std::string value)
Parse from a string.
std::string m_default
The default value, as a string, if it exists.
Definition: command-line.h:499
virtual ~Item()
Destructor.
virtual bool HasDefault() const
std::string m_name
Argument label: --m_name=...
Definition: command-line.h:428
std::string m_help
Argument help string.
Definition: command-line.h:429
Extension of Item for strings.
Definition: command-line.h:470
bool Parse(const std::string value)
Parse from a string.
std::string m_value
The argument value.
Definition: command-line.h:477
std::string GetDefault(void) const
Parse command-line arguments.
Definition: command-line.h:229
void PrintAttributeList(std::ostream &os, const TypeId tid, std::stringstream &header) const
Print the Attributes for a single type.
void PrintGroups(std::ostream &os) const
Handler for --PrintGroups: print all TypeId group names.
void PrintTypeIds(std::ostream &os) const
Handler for --PrintTypeIds: print all TypeId names.
std::string GetExtraNonOption(std::size_t i) const
Get extra non-option arguments by index.
void HandleArgument(const std::string &name, const std::string &value) const
Match name against the program or general arguments, and dispatch to the appropriate handler.
std::size_t m_nonOptionCount
The number of actual non-option arguments seen so far.
Definition: command-line.h:595
~CommandLine()
Destructor.
std::string GetName() const
Get the program name.
Items m_options
The list of option arguments.
Definition: command-line.h:592
bool HandleNonOption(const std::string &value)
Handle a non-option.
std::vector< Item * > Items
Argument list container.
Definition: command-line.h:591
void Parse(int argc, char *argv[])
Parse the program arguments.
void PrintGroup(std::ostream &os, const std::string &group) const
Handler for --PrintGroup: print all types belonging to a given group.
void Copy(const CommandLine &cmd)
Copy constructor.
std::size_t m_NNonOptions
The expected number of non-option arguments.
Definition: command-line.h:594
void Clear(void)
Remove all arguments, Usage(), name.
void PrintGlobals(std::ostream &os) const
Handler for --PrintGlobals: print all global variables and values.
Items m_nonOptions
The list of non-option arguments.
Definition: command-line.h:593
void PrintVersion(std::ostream &os) const
Print ns-3 version to the desired output stream.
std::string m_shortName
The source file name (without .cc), as would be given to ns3 run
Definition: command-line.h:597
void Usage(const std::string usage)
Supply the program usage and documentation.
bool HandleOption(const std::string &param) const
Handle an option in the form param=value.
std::string m_usage
The Usage string.
Definition: command-line.h:596
void PrintAttributes(std::ostream &os, const std::string &type) const
Handler for --PrintAttributes: print the attributes for a given type as well as its parents.
CommandLine(void)
Constructor.
void AddValue(const std::string &name, const std::string &help, T &value)
Add a program argument, assigning to POD.
Definition: command-line.h:670
std::size_t GetNExtraNonOptions(void) const
Get the total number of non-option arguments found, including those configured with AddNonOption() an...
void PrintHelp(std::ostream &os) const
Print program usage to the desired output stream.
std::string GetVersion() const
Get the program version.
CommandLine & operator=(const CommandLine &cmd)
Assignment.
static bool HandleAttribute(const std::string name, const std::string value)
Callback function to handle attributes.
void PrintDoxygenUsage(void) const
Append usage message in Doxygen format to the file indicated by the NS_COMMANDLINE_INTROSPECTION envi...
void Initialize(std::vector< std::string > args, std::string outDir="")
Open the DesMetrics trace file and print the header.
Definition: des-metrics.cc:42
static Iterator End(void)
The End iterator.
static Iterator Begin(void)
The Begin iterator.
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:74
static DesMetrics * Get(void)
Get a pointer to the singleton instance.
Definition: singleton.h:100
Hold variables of type string.
Definition: string.h:41
std::string Get(void) const
Definition: string.cc:31
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:103
TimeWithUnit As(const enum Unit unit=Time::AUTO) const
Attach a unit to a Time, to facilitate output in a specific unit.
Definition: time.cc:418
a unique identifier for an interface.
Definition: type-id.h:59
std::size_t GetAttributeN(void) const
Get the number of attributes.
Definition: type-id.cc:1076
static uint16_t GetRegisteredN(void)
Get the number of registered TypeIds.
Definition: type-id.cc:869
std::string GetAttributeFullName(std::size_t i) const
Get the Attribute name by index.
Definition: type-id.cc:1089
struct TypeId::AttributeInformation GetAttribute(std::size_t i) const
Get Attribute information by index.
Definition: type-id.cc:1083
std::string GetGroupName(void) const
Get the group name.
Definition: type-id.cc:968
static TypeId GetRegistered(uint16_t i)
Get a TypeId by index.
Definition: type-id.cc:875
TypeId GetParent(void) const
Get the parent of this TypeId.
Definition: type-id.cc:943
std::string GetName(void) const
Get the name.
Definition: type-id.cc:976
bool LookupAttributeByName(std::string name, struct AttributeInformation *info) const
Find an Attribute by name, retrieving the associated AttributeInformation.
Definition: type-id.cc:882
static bool LookupByNameFailSafe(std::string name, TypeId *tid)
Get a TypeId by name.
Definition: type-id.cc:837
static std::string LongVersion(void)
Constructs a string containing all of the build details.
Definition: version.cc:132
ns3::CommandLine declaration.
Declaration of the various ns3::Config functions and classes.
ns3::DesMetrics declaration.
ns3::GlobalValue declaration.
#define NS_ASSERT_MSG(condition, message)
At runtime, in debugging builds, if this condition is not true, the program prints the message to out...
Definition: assert.h:88
std::string GetDefault< Time >(const Time &val)
Helper to specialize CommandLine::UserItem::GetDefault() on types needing special handling.
std::string GetDefault< bool >(const bool &val)
Helper to specialize CommandLine::UserItem::GetDefault() on types needing special handling.
bool SetGlobalFailSafe(std::string name, const AttributeValue &value)
Definition: config.cc:896
bool SetDefaultFailSafe(std::string fullName, const AttributeValue &value)
Definition: config.cc:857
#define NS_FATAL_ERROR(msg)
Report a fatal error with a message and terminate.
Definition: fatal-error.h:165
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:205
#define NS_LOG_DEBUG(msg)
Use NS_LOG to output a message of level LOG_DEBUG.
Definition: log.h:273
#define NS_LOG_LOGIC(msg)
Use NS_LOG to output a message of level LOG_LOGIC.
Definition: log.h:289
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
#define NS_LOG_WARN(msg)
Use NS_LOG to output a message of level LOG_WARN.
Definition: log.h:265
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Definition: log.h:281
Callback< R > MakeBoundCallback(R(*fnPtr)(TX), ARG a1)
Make Callbacks with one bound argument.
Definition: callback.h:1709
std::list< std::string > Split(std::string path)
Split a file system path into directories according to the local path separator.
Definition: system-path.cc:258
std::string Append(std::string left, std::string right)
Join two file system path elements.
Definition: system-path.cc:241
Debug message logging.
std::string Encode(const std::string &source)
HTML-encode a string, for PrintDoxygenUsage().
Definition: command-line.cc:61
bool UserItemParse< bool >(const std::string value, bool &val)
Specialization of CommandLine::UserItem to bool.
bool UserItemParse< uint8_t >(const std::string value, uint8_t &val)
Specialization of CommandLine::UserItem to uint8_t to distinguish from char.
Every class exported by the ns3 library is enclosed in the ns3 namespace.
std::ostream & operator<<(std::ostream &os, const Angles &a)
Definition: angles.cc:139
cmd
Definition: second.py:35
ns3::StringValue attribute value declarations.
Attribute implementation.
Definition: type-id.h:78
Ptr< const AttributeChecker > checker
Checker object.
Definition: type-id.h:92
Ptr< const AttributeValue > initialValue
Configured initial value.
Definition: type-id.h:88
std::string help
Attribute help string.
Definition: type-id.h:82
ns3::SystemPath declarations.
ns3::TypeId declaration; inline and template implementations.
class ns3::Version definition