[ < ] [ > ]   [ << ] [ 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 first.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,

  ~/repos/ns-3-dev > ./waf --run "scratch/first --PrintHelp"

This will ask Waf to run the scratch/first 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,

  ~/repos/ns-3-dev > ./waf --run ``scratch/first --PrintHelp''
  Entering directory `/home/craigdo/repos/ns-3-dev/build'
  Compilation finished successfully
  --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.
  ~/repos/ns-3-dev >

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/first --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 first.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,

  ~/repos/ns-3-dev > ./waf --run scratch/first
  Entering directory `/home/craigdo/repos/ns-3-dev/build'
  Compilation finished successfully
  0ns UdpEchoServerApplication:UdpEchoServer()
  1000000000ns UdpEchoServerApplication:StartApplication()
  Sent 1024 bytes to 10.1.1.2
  2257324218ns Received 1024 bytes from 10.1.1.1
  2257324218ns Echoing packet
  Received 1024 bytes from 10.1.1.2
  10000000000ns UdpEchoServerApplication:StopApplication()
  UdpEchoServerApplication:DoDispose()
  UdpEchoServerApplication:~UdpEchoServer()
  ~/repos/ns-3-dev >

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.0036864 seconds. Now it is receiving the packet at about 2.257 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/first --ns3::PointToPointNetDevice::DataRate=5Mbps"

This will set the default value of the DataRate attribute back to five megabits per second. To get the original behavior of the script back, we will have to set the speed-of-light delay of the channel. We can ask the command line system to print out the Attributes of the channel just like we did the net device:

  ./waf --run "scratch/first --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/first
    --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:

  Compilation finished successfully
  0ns UdpEchoServerApplication:UdpEchoServer()
  1000000000ns UdpEchoServerApplication:StartApplication()
  Sent 1024 bytes to 10.1.1.2
  2003686400ns Received 1024 bytes from 10.1.1.1
  2003686400ns Echoing packet
  Received 1024 bytes from 10.1.1.2
  10000000000ns UdpEchoServerApplication:StopApplication()
  UdpEchoServerApplication:DoDispose()
  UdpEchoServerApplication:~UdpEchoServer()

Note that the packet is again received by the server at 2.0036864 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 in the script. Then you have to rebuild the script using the default. You will also have to find the syntax for actually setting the new default atribute 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/first 
    --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/first.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.SetAppAttribute ("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.

  ~/repos/ns-3-dev > ./waf --run "scratch/first --PrintHelp"
  Entering directory `/home/craigdo/repos/ns-3-dev/build'
  Compilation finished successfully
  --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
  ~/repos/ns-3-dev >

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,

  ~/repos/ns-3-dev > ./waf --run "scratch/first --nPackets=2"
  Entering directory `/home/craigdo/repos/ns-3-dev/build'
  Compilation finished successfully
  Sent 1024 bytes to 10.1.1.2
  Received 1024 bytes from 10.1.1.1
  Received 1024 bytes from 10.1.1.2
  Sent 1024 bytes to 10.1.1.2
  Received 1024 bytes from 10.1.1.1
  Received 1024 bytes from 10.1.1.2
  ~/repos/ns-3-dev >

You have now echoed two packets.

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 December, 19 2008 using texi2html 1.78.