[ < ] [ > ]   [ << ] [ Up ] [ >> ]         [Top] [Contents] [Index] [ ? ]

5.2 Using Command Line Arguments


[ < ] [ > ]   [ << ] [ Up ] [ >> ]         [Top] [Contents] [Index] [ ? ]

5.2.1 Overriding Default Attributes

Another way you can change how ns-3 scripts behave without editing and building is via command line arguments. We provide a mechanism to parse command line arguments and automatically set local and global variables based on those arguments.

The first step in using the command line argument system is to declare the command line parser. This is done quite simply (in your main program) as in the following code,

    int
  main (int argc, char *argv[])
  {
    ...  

    CommandLine cmd;
    cmd.Parse (argc, argv);

    ...
  }

This simple two line snippet is actually very useful by itself. It opens the door to the ns-3 global variable and Attribute systems. Go ahead and add that two lines of code to the scratch/myfirst.cc script at the start of main. Go ahead and build the script and run it, but ask the script for help in the following way,

  ./waf --run "scratch/myfirst --PrintHelp"

This will ask Waf to run the scratch/myfirst script and pass the command line argument --PrintHelp to the script. The quotes are required to sort out which program gets which argument. The command line parser will now see the --PrintHelp argument and respond with,

  Waf: Entering directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  Waf: Leaving directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  'build' finished successfully (0.413s)
  TcpL4Protocol:TcpStateMachine()
  CommandLine:HandleArgument(): Handle arg name=PrintHelp value=
  --PrintHelp: Print this help message.
  --PrintGroups: Print the list of groups.
  --PrintTypeIds: Print all TypeIds.
  --PrintGroup=[group]: Print all TypeIds of group.
  --PrintAttributes=[typeid]: Print all attributes of typeid.
  --PrintGlobals: Print the list of globals.

Let’s focus on the --PrintAttributes option. We have already hinted at the ns-3 Attribute system while walking through the first.cc script. We looked at the following lines of code,

    PointToPointHelper pointToPoint;
    pointToPoint.SetDeviceAttribute ("DataRate", StringValue ("5Mbps"));
    pointToPoint.SetChannelAttribute ("Delay", StringValue ("2ms"));

and mentioned that DataRate was actually an Attribute of the PointToPointNetDevice. Let’s use the command line argument parser to take a look at the Attributes of the PointToPointNetDevice. The help listing says that we should provide a TypeId. This corresponds to the class name of the class to which the Attributes belong. In this case it will be ns3::PointToPointNetDevice. Let’s go ahead and type in,

  ./waf --run "scratch/myfirst --PrintAttributes=ns3::PointToPointNetDevice"

The system will print out all of the Attributes of this kind of net device. Among the Attributes you will see listed is,

  --ns3::PointToPointNetDevice::DataRate=[32768bps]:
    The default data rate for point to point links

This is the default value that will be used when a PointToPointNetDevice is created in the system. We overrode this default with the Attribute setting in the PointToPointHelper above. Let’s use the default values for the point-to-point devices and channels by deleting the SetDeviceAttribute call and the SetChannelAttribute call from the myfirst.cc we have in the scratch directory.

Your script should now just declare the PointToPointHelper and not do any set operations as in the following example,

  ...

  NodeContainer nodes;
  nodes.Create (2);

  PointToPointHelper pointToPoint;

  NetDeviceContainer devices;
  devices = pointToPoint.Install (nodes);

  ...

Go ahead and build the new script with Waf (./waf) and let’s go back and enable some logging from the UDP echo server application and turn on the time prefix.

  export 'NS_LOG=UdpEchoServerApplication=level_all|prefix_time'

If you run the script, you should now see the following output,

  Waf: Entering directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  Waf: Leaving directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  'build' finished successfully (0.405s)
  0s UdpEchoServerApplication:UdpEchoServer()
  1s UdpEchoServerApplication:StartApplication()
  Sent 1024 bytes to 10.1.1.2
  2.25732s Received 1024 bytes from 10.1.1.1
  2.25732s Echoing packet
  Received 1024 bytes from 10.1.1.2
  10s UdpEchoServerApplication:StopApplication()
  UdpEchoServerApplication:DoDispose()
  UdpEchoServerApplication:~UdpEchoServer()

Recall that the last time we looked at the simulation time at which the packet was received by the echo server, it was at 2.00369 seconds.

  2.00369s UdpEchoServerApplication:HandleRead(): Received 1024 bytes from 10.1.1.1

Now it is receiving the packet at 2.25732 seconds. This is because we just dropped the data rate of the PointToPointNetDevice down to its default of 32768 bits per second from five megabits per second.

If we were to provide a new DataRate using the command line, we could speed our simulation up again. We do this in the following way, according to the formula implied by the help item:

  ./waf --run "scratch/myfirst --ns3::PointToPointNetDevice::DataRate=5Mbps"

This will set the default value of the DataRate Attribute back to five megabits per second. Are you surprised by the result? It turns out that in order to get the original behavior of the script back, we will have to set the speed-of-light delay of the channel as well. We can ask the command line system to print out the Attributes of the channel just like we did for the net device:

  ./waf --run "scratch/myfirst --PrintAttributes=ns3::PointToPointChannel"

We discover the Delay Attribute of the channel is set in the following way:

  --ns3::PointToPointChannel::Delay=[0ns]:
    Transmission delay through the channel

We can then set both of these default values through the command line system,

  ./waf --run "scratch/myfirst
    --ns3::PointToPointNetDevice::DataRate=5Mbps
    --ns3::PointToPointChannel::Delay=2ms"

in which case we recover the timing we had when we explicitly set the DataRate and Delay in the script:

  Waf: Entering directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  Waf: Leaving directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  'build' finished successfully (0.417s)
  0s UdpEchoServerApplication:UdpEchoServer()
  1s UdpEchoServerApplication:StartApplication()
  Sent 1024 bytes to 10.1.1.2
  2.00369s Received 1024 bytes from 10.1.1.1
  2.00369s Echoing packet
  Received 1024 bytes from 10.1.1.2
  10s UdpEchoServerApplication:StopApplication()
  UdpEchoServerApplication:DoDispose()
  UdpEchoServerApplication:~UdpEchoServer()

Note that the packet is again received by the server at 2.00369 seconds. We could actually set any of the Attributes used in the script in this way. In particular we could set the UdpEchoClient Attribute MaxPackets to some other value than one.

How would you go about that? Give it a try. Remember you have to comment out the place we override the default Attribute and explicitly set MaxPackets in the script. Then you have to rebuild the script. You will also have to find the syntax for actually setting the new default attribute value using the command line help facility. Once you have this figured out you should be able to control the number of packets echoed from the command line. Since we’re nice folks, we’ll tell you that your command line should end up looking something like,

  ./waf --run "scratch/myfirst 
    --ns3::PointToPointNetDevice::DataRate=5Mbps 
    --ns3::PointToPointChannel::Delay=2ms 
    --ns3::UdpEchoClient::MaxPackets=2"

[ < ] [ > ]   [ << ] [ Up ] [ >> ]         [Top] [Contents] [Index] [ ? ]

5.2.2 Hooking Your Own Values

You can also add your own hooks to the command line system. This is done quite simply by using the AddValue method to the command line parser.

Let’s use this facility to specify the number of packets to echo in a completely different way. Let’s add a local variable called nPackets to the main function. We’ll initialize it to one to match our previous default behavior. To allow the command line parser to change this value, we need to hook the value into the parser. We do this by adding a call to AddValue. Go ahead and change the scratch/myfirst.cc script to start with the following code,

  int
  main (int argc, char *argv[])
  {
    uint32_t nPackets = 1;

    CommandLine cmd;
    cmd.AddValue("nPackets", "Number of packets to echo", nPackets);
    cmd.Parse (argc, argv);

    ...

Scroll down to the point in the script where we set the MaxPackets Attribute and change it so that it is set to the variable nPackets instead of the constant 1 as is shown below.

  echoClient.SetAttribute ("MaxPackets", UintegerValue (nPackets));

Now if you run the script and provide the --PrintHelp argument, you should see your new User Argument listed in the help display.

Try,

  ./waf --run "scratch/myfirst --PrintHelp"
  Waf: Entering directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  Waf: Leaving directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  'build' finished successfully (0.403s)
  --PrintHelp: Print this help message.
  --PrintGroups: Print the list of groups.
  --PrintTypeIds: Print all TypeIds.
  --PrintGroup=[group]: Print all TypeIds of group.
  --PrintAttributes=[typeid]: Print all attributes of typeid.
  --PrintGlobals: Print the list of globals.
  User Arguments:
      --nPackets: Number of packets to echo

If you want to specify the number of packets to echo, you can now do so by setting the --nPackets argument in the command line,

  ./waf --run "scratch/myfirst --nPackets=2"

You should now see

  Waf: Entering directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  Waf: Leaving directory `/home/craigdo/repos/ns-3-allinone/ns-3-dev/build'
  'build' finished successfully (0.404s)
  0s UdpEchoServerApplication:UdpEchoServer()
  1s UdpEchoServerApplication:StartApplication()
  Sent 1024 bytes to 10.1.1.2
  2.25732s Received 1024 bytes from 10.1.1.1
  2.25732s Echoing packet
  Received 1024 bytes from 10.1.1.2
  Sent 1024 bytes to 10.1.1.2
  3.25732s Received 1024 bytes from 10.1.1.1
  3.25732s Echoing packet
  Received 1024 bytes from 10.1.1.2
  10s UdpEchoServerApplication:StopApplication()
  UdpEchoServerApplication:DoDispose()
  UdpEchoServerApplication:~UdpEchoServer()

You have now echoed two packets. Pretty easy, isn’t it?

You can see that if you are an ns-3 user, you can use the command line argument system to control global values and Attributes. If you are a model author, you can add new Attributes to your Objects and they will automatically be available for setting by your users through the command line system. If you are a script author, you can add new variables to your scripts and hook them into the command line system quite painlessly.


[ < ] [ > ]   [ << ] [ Up ] [ >> ]

This document was generated on August 20, 2010 using texi2html 1.82.