1.1 --- a/doc/tutorial/introduction.texi Tue Feb 05 15:29:17 2008 -0500
1.2 +++ b/doc/tutorial/introduction.texi Tue Feb 05 15:30:16 2008 -0500
1.3 @@ -4,103 +4,209 @@
1.4 @c ========================================================================
1.5
1.6 @c ========================================================================
1.7 -@c Introduction
1.8 +@c Tutorial Goals
1.9 @c ========================================================================
1.10
1.11 -@node Introduction
1.12 -@chapter Introduction
1.13 +@node Tutorial Goals
1.14 +@unnumbered Tutorial Goals
1.15
1.16 -The @command{ns-3} simulator is a discrete-event network
1.17 +@c This is an unnumbered section, like a preface. Numbering
1.18 +@c starts with section 1 (Introduction)
1.19 +
1.20 +The goal of this ns-3 tutorial is to introduce new users of ns-3 to enough
1.21 +of the system to enable them to author simple simulation scripts and extract
1.22 +useful information from the simulations. We begin by introducing some of the
1.23 +other important resources that are available to those interested in using or
1.24 +writing scripts, models and even those interested in making contributions to
1.25 +the core ns-3 system. We provide an overview of some of the
1.26 +important abstractions, design patterns and idioms used when writing
1.27 +ns-3 scripts, and then dig right in by begining to write simulation
1.28 +scripts, run them and interpret results.
1.29 +
1.30 +After completing this tutorial, one should be able to:
1.31 +@itemize @bullet
1.32 +@item Find documentation resources in the distribution and on the web;
1.33 +@item Download and compile the ns-3 system;
1.34 +@item Understand the key software conventions of ns-3;
1.35 +@item Modify configuration parameters of existing scripts;
1.36 +@item Change the simulation output (tracing, logging, statistics);
1.37 +@item Extend the simulator to use new objects
1.38 +@item Write new ns-3 applications;
1.39 +@item See how to port code from ns-2;
1.40 +@item ... (more to follow)
1.41 +@end itemize
1.42 +
1.43 +@c ========================================================================
1.44 +@c PART: Introduction
1.45 +@c ========================================================================
1.46 +@c The below chapters are under the major heading "Introduction"
1.47 +@c This is similar to the Latex \part command
1.48 +@c
1.49 +@c ========================================================================
1.50 +@c Overview
1.51 +@c ========================================================================
1.52 +@node Overview
1.53 +@chapter Overview
1.54 +
1.55 +@menu
1.56 +* For ns-2 users::
1.57 +* Contributing::
1.58 +* Tutorial organization::
1.59 +@end menu
1.60 +
1.61 +The ns-3 simulator is a discrete-event network
1.62 simulator targeted primarily for research and educational use.
1.63 -The @uref{http://www.nsnam.org,,@command{ns-3} project}, started in
1.64 +The @uref{http://www.nsnam.org,,ns-3 project}, started in
1.65 2006, is an open-source project. The goal of the project is to
1.66 -build a new netework simulator primarily for research and educational use.
1.67 +build a new network simulator primarily for research and educational use.
1.68
1.69 -The purpose of this tutorial is to introduce new @command{ns-3} users to the
1.70 +Primary documentation for the ns-3 project is available in
1.71 +three forms:
1.72 +@itemize @bullet
1.73 +@item @uref{http://www.nsnam.org/doxygen/index.html,,ns-3 Doxygen/Manual}: Documentation of the public APIs of the simulator
1.74 +@item Tutorial (this document)
1.75 +@item @uref{http://www.nsnam.org/wiki/index.php,, ns-3 wiki}
1.76 +@end itemize
1.77 +
1.78 +The purpose of this tutorial is to introduce new ns-3 users to the
1.79 system in a structured way. It is sometimes difficult for new users to
1.80 glean essential information from detailed manuals and to convert this
1.81 information into working simulations. In this tutorial, we will build
1.82 several example simulations, introducing and explaining key concepts and
1.83 features as we go.
1.84
1.85 -As the tutorial unfolds, we will introduce the full @command{ns-3}
1.86 +As the tutorial unfolds, we will introduce the full ns-3
1.87 documentation
1.88 and provide pointers to source code for those interested in delving deeper
1.89 into the workings of the system.
1.90
1.91 -Primary documentation for the @command{ns-3} project is available in
1.92 -three forms:
1.93 -@itemize @bullet
1.94 -@item ns-3 Manual: Documentation of the public APIs of the simulator
1.95 -@item Tutorial (this document)
1.96 -@item ns-3 wiki (http://www.nsnam.org/wiki/index.php)
1.97 -@end itemize
1.98 -
1.99 A few key points are worth noting at the onset:
1.100 @itemize @bullet
1.101 -@item @command{ns-3} is not an extension of @command{ns-2}; it is a new
1.102 -simulator. The two simulators are both written in C++ but @command{ns-3}
1.103 -is a new simulator that does not support the @command{ns-2} APIs.
1.104 -Some models from @command{ns-2} have already been ported from @command{ns-2}
1.105 -to @command{ns-3}. The project will continue to maintain @command{ns-2} while
1.106 -@command{ns-3} is being built, and will study transition and
1.107 +@item ns-3 is not an extension of @uref{http://www.isi.edu/nsnam/ns,,ns-2};
1.108 +it is a new
1.109 +simulator. The two simulators are both written in C++ but ns-3
1.110 +is a new simulator that does not support the ns-2 APIs.
1.111 +Some models from ns-2 have already been ported from ns-2
1.112 +to ns-3. The project will continue to maintain ns-2 while
1.113 +ns-3 is being built, and will study transition and
1.114 integration mechanisms.
1.115 -@item @command{ns-3} is open-source, and the project strives to maintain
1.116 +@item ns-3 is open-source, and the project strives to maintain
1.117 an open environment for researchers to contribute and share their
1.118 software.
1.119 @end itemize
1.120
1.121 -The goal of this tutorial is to introduce new users of @command{ns-3} to enough
1.122 -of the system to enable them to author simple simulation scripts and extract
1.123 -useful information from the simulations. We begin by introducing some of the
1.124 -other important resources that are available to those interested in using or
1.125 -writing scripts, models and even those interested in making contributions to
1.126 -the core @command{ns-3} system. We provide an overview of some of the
1.127 -important abstractions, design patterns and idioms used when writing
1.128 -@command{ns-3} scripts, and then dig right in by begining to write simulation
1.129 -scripts, run them and interpret results.
1.130 +@node For ns-2 users
1.131 +@section For ns-2 users
1.132
1.133 -After completing this tutorial, one should be able to:
1.134 +For those familiar with ns-2, the most visible outward change
1.135 +when moving to ns-3 is the choice of scripting language.
1.136 +ns-2 is typically scripted in Tcl and results of simulations can
1.137 +be visualized using the Network Animator @command{nam}. In
1.138 +ns-3 there is currently no visualization module, and Python
1.139 +bindings have been developed (Tcl bindings have been prototyped
1.140 +using @uref{http://www.swig.org,,SWIG}, but are not supported by the
1.141 +current development team).
1.142 +In this tutorial, we will concentrate on
1.143 +scripting directly in C++ and interpreting results via trace files.
1.144 +
1.145 +But there are similarities as well (both, for example, are based
1.146 +on C++ objects, and some code from ns-2 has already been ported
1.147 +to ns-3). We will try to highlight differences between ns-2 and ns-3
1.148 +as we proceed in this tutorial.
1.149 +
1.150 +@node Contributing
1.151 +@section Contributing
1.152 +
1.153 +@cindex software configuration management
1.154 +ns-3 is a research and educational simulator, by and for the
1.155 +research community. It will rely on the ongoing contributions of
1.156 +the community to develop new models, debug or maintain
1.157 +existing ones, and share results. There are a few policies
1.158 +that we hope will encourage people to contribute to ns-3 like they
1.159 +have for ns-2:
1.160 @itemize @bullet
1.161 -@item Find documentation resources in the distribution and on the web;
1.162 -@item Download and compile the @command{ns-3} system;
1.163 -@item Use the provided devices to author network simulations of fairly
1.164 -significant complexity;
1.165 -@item Use the default value system to configure simulations;
1.166 -@item Write new @command{ns-3} applications;
1.167 -@item Use the tracing subsystem.
1.168 +@item open source licensing based on GNU GPLv2 compatibility
1.169 +@item @uref{http://www.nsnam.org/wiki/index.php,,wiki}
1.170 +@item @uref{http://www.nsnam.org/wiki/index.php/Contributed_Code,,Contributed Code} page, similar to ns-2's popular
1.171 +@uref{http://nsnam.isi.edu/nsnam/index.php/Contributed_Code,,Contributed Code}
1.172 +page
1.173 +@item @code{src/contrib} directory (we will host your contributed code)
1.174 +@item open @uref{http://www.nsnam.org/bugzilla,,bug tracker}
1.175 +@item ns-3 developers will gladly help potential contributors to get
1.176 +started with the simulator (please contact @uref{http://www.nsnam.org/people.html,,one of us})
1.177 +@end itemize
1.178 +
1.179 +If you are an ns user, please consider to provide your feedback,
1.180 +bug fixes, or code to the project.
1.181 +
1.182 +@node Tutorial organization
1.183 +@section Tutorial organization
1.184 +
1.185 +The tutorial assumes that new users might follow a path such as follows:
1.186 +
1.187 +@itemize @bullet
1.188 +@item browse the source code and documentation, to get a feel for
1.189 +the simulator and what it might be like to handle;
1.190 +@item try to download and build a copy;
1.191 +@item try to run a few sample programs, and perhaps change some configurations;
1.192 +@item look at simulation output, and try to adjust it
1.193 +@item study the software architecture of the system, to consider hacking it or
1.194 +extending it;
1.195 +@item write new models or port existing code to ns-3, and eventually post those
1.196 +models back to the community.
1.197 @end itemize
1.198
1.199 +As a result, we have tried to organize the tutorial along the above
1.200 +broad sequences of events.
1.201 +
1.202 @c ========================================================================
1.203 -@c Overview
1.204 +@c Browsing ns-3
1.205 @c ========================================================================
1.206
1.207 -@node Overview
1.208 -@chapter Overview
1.209 +@node Browsing
1.210 +@chapter Browsing ns-3
1.211
1.212 -This chapter is a brief tour of @command{ns-3}. It introduces the
1.213 -concept of discrete event simulation, provides a brief overview of
1.214 -@command{ns-3}, and provides a short contextual introduction for
1.215 -the existing @command{ns-2} user community.
1.216 +@menu
1.217 +* Source code::
1.218 +* Doxygen::
1.219 +* Other documentation::
1.220 +@end menu
1.221
1.222 -@node Discrete Event Simulation
1.223 -@section Discrete Event Simulation
1.224 +@node Source code
1.225 +@section Source code
1.226
1.227 -@node ns-3 Overview
1.228 -@section ns-3 Overview
1.229 +The most recent code can be browsed on our web server at the following link:
1.230 +@uref{http://code.nsnam.org/?sort=lastchange}. If you click on the bold
1.231 +repository names on the left of the page, you will see changelogs for
1.232 +these repositories, and links to the @emph{manifest}. From the manifest
1.233 +links, one can browse the source tree.
1.234
1.235 -@node For ns-2 users
1.236 -@section For @command{ns-2} users
1.237 +The top-level directory will look something like:
1.238 +@verbatim
1.239 + AUTHORS RELEASE_NOTES examples/ src/ waf*
1.240 + LICENSE VERSION ns3/ tutorial/ waf.bat*
1.241 + README doc/ samples/ utils/ wscript
1.242 +@end verbatim
1.243 +The source code is mainly in the @code{src} directory. Example
1.244 +scripts are in the @code{examples} directory. Both are good directories
1.245 +to start browsing some code.
1.246
1.247 -For those familiar with @command{ns-2}, the most visible outward change
1.248 -when moving to @command{ns-3} is the choice of scripting language.
1.249 -@command{ns-2} is typically scripted in Tcl and results of simulations are
1.250 -often visualized using the Network Animator @command{nam}. In
1.251 -@command{ns-3} there is currently no visualization module, and multiple
1.252 -language bindings are allowed. In this tutorial, we will concentrate on
1.253 -scripting directly in C++ and interpreting results via trace files. Scripting
1.254 -in other languages will typically be done via straightforward bindings of the
1.255 -target language into the underlying C++.
1.256 +For ns-2 users, who may be familiar with the @code{simple.tcl} example script
1.257 +in the ns-2 documentation, an analogous script is found in
1.258 +@code{examples/simple-point-to-point.cc} with a Python equivalent found
1.259 +in @emph{(pending Python merge)}.
1.260 +
1.261 +@node Doxygen
1.262 +@section Doxygen
1.263 +
1.264 +We document all of APIs using @uref{http://www.stack.nl/~dimitri/doxygen/,,Doxygen}. Current builds of this documentation are available at:
1.265 +@uref{http://www.nsnam.org/doxygen/index.html}, which are worth an initial
1.266 +look.
1.267 +
1.268 +@node Other documentation
1.269 +@section Other documentation
1.270 +
1.271 +See: @uref{http://www.nsnam.org/documents.html}.
1.272
1.273 @c ========================================================================
1.274 @c Resources
1.275 @@ -121,9 +227,9 @@
1.276 @section The Web
1.277
1.278 @cindex www.nsnam.org
1.279 -There are several important resources of which any @command{ns-3} user must be
1.280 +There are several important resources of which any ns-3 user must be
1.281 aware. The main web site is located at @uref{http://www.nsnam.org}
1.282 -and provides access to basic information about the @command{ns-3} system.
1.283 +and provides access to basic information about the ns-3 system.
1.284 Detailed documentation is available through the main web site at
1.285 @uref{http://www.nsnam.org/documents.html}.
1.286
1.287 @@ -133,7 +239,7 @@
1.288 and also gain access to the detailed software documentation. The software
1.289 system is documented in great detail using
1.290 @uref{http://www.stack.nl/~dimitri/doxygen/,,Doxygen}. There is a Wiki that
1.291 -complements the main @command{ns-3} web site which you will find at
1.292 +complements the main ns-3 web site which you will find at
1.293 @uref{http://www.nsnam.org/wiki/}.
1.294
1.295 You will find user and developer FAQs there as well as troubleshooting guides,
1.296 @@ -157,7 +263,7 @@
1.297
1.298 @cindex software configuration management
1.299 @cindex Mercurial
1.300 -The @command{ns-3} project uses Mercurial as its source code management system.
1.301 +The ns-3 project uses Mercurial as its source code management system.
1.302 Although you do not need to know much about Mercurial in order to complete
1.303 this tutorial, we recommend becoming familiar with Mercurial and using it
1.304 to access the source code. Mercurial has a web site at
1.305 @@ -169,8 +275,8 @@
1.306 and a QuickStart guide at
1.307 @uref{http://www.selenic.com/mercurial/wiki/index.cgi/QuickStart/}.
1.308
1.309 -You can also find vital information about using Mercurial and @command{ns-3}
1.310 -on the main @command{ns-3} web site.
1.311 +You can also find vital information about using Mercurial and ns-3
1.312 +on the main ns-3 web site.
1.313
1.314 @node Waf
1.315 @section Waf
1.316 @@ -187,9 +293,9 @@
1.317 alternatives have been developed. Recently these systems have been developed
1.318 using the Python language.
1.319
1.320 -The build system @code{Waf} is used on the @command{ns-3} project. It is one
1.321 +The build system @code{Waf} is used on the ns-3 project. It is one
1.322 of the new generation of Python-based build systems. You will not need to
1.323 -understand any Python to build the existing @command{ns-3} system, and will
1.324 +understand any Python to build the existing ns-3 system, and will
1.325 only have to understand a tiny and intuitively obvious subset of Python in
1.326 order to extend the system in most cases.
1.327
1.328 @@ -200,7 +306,7 @@
1.329 @section Environment, Idioms, and Design Patterns
1.330
1.331 @cindex C++
1.332 -As mentioned above, scripting in @command{ns-3} is done in C++. A working
1.333 +As mentioned above, scripting in ns-3 is done in C++. A working
1.334 knowledge of C++ and object-oriented concepts is assumed in this document.
1.335 We will take some time to review some of the more advanced concepts or
1.336 possibly unfamiliar language features, idioms and design patterns as they
1.337 @@ -217,26 +323,26 @@
1.338
1.339 @cindex toolchain
1.340 @cindex GNU
1.341 -The @command{ns-3} system uses the GNU ``toolchain'' for development.
1.342 +The ns-3 system uses the GNU ``toolchain'' for development.
1.343 A software toolchain is the set of programming tools available in the given
1.344 environment. For a quick review of what is included in the GNU toolchain see,
1.345 @uref{http://en.wikipedia.org/wiki/GNU_toolchain}.
1.346
1.347 @cindex Linux
1.348 -Typically a @command{ns-3} author will work in Linux or a Linux-like
1.349 +Typically an ns-3 author will work in Linux or a Linux-like
1.350 environment. For those running under Windows, there do exist environments
1.351 -which simulate the Linux environment to various degrees. The @command{ns-3}
1.352 +which simulate the Linux environment to various degrees. The ns-3
1.353 project supports development in the Cygwin and the MinGW environments for
1.354 these users. See @uref{http://www.cygwin.com/} and
1.355 @uref{http://www.mingw.org/} for details on downloading and using these
1.356 -systems. I use Cygwin in these cases since it provides all of the Linux tools
1.357 -I know and love. It can, however, sometimes be problematic due to the way it
1.358 +systems. Cygwin provides many of the popular Linux system commands.
1.359 +It can, however, sometimes be problematic due to the way it
1.360 actually does its emulation, and sometimes interactions with other Windows
1.361 software can cause problems.
1.362
1.363 @cindex Cygwin
1.364 @cindex MinGW
1.365 -If you do use Cygwin or MinGW; and use Logitech products, I will save you
1.366 +If you do use Cygwin or MinGW; and use Logitech products, we will save you
1.367 quite a bit of heartburn right off the bat and encourage you to take a look
1.368 at the @uref{http://www.mingw.org/MinGWiki/index.php/FAQ,,MinGW FAQ}.
1.369
1.370 @@ -254,7 +360,7 @@
1.371 In any system, there are a number of problems to be solved that happen
1.372 repeatedly. Often the solutions to these problems can be generalized and
1.373 applied in a similar way across the system. These solutions are called
1.374 -Design Patterns. The @command{ns-3} system relies on several classic design
1.375 +Design Patterns. The ns-3 system relies on several classic design
1.376 patterns.
1.377
1.378 @cindex design pattern
1.379 @@ -269,34 +375,34 @@
1.380
1.381 These low-level constructs, or idioms, extend upward in complexity, eventually
1.382 becoming implementations of design patterns. As you are exposed to more
1.383 -and more of the @command{ns-3} system, you will begin to recognize and be
1.384 +and more of the ns-3 system, you will begin to recognize and be
1.385 comfortable with the C++ implementations (idioms) of several important design
1.386 patterns.
1.387
1.388 @cindex functor
1.389 @cindex callback
1.390 @cindex smart pointer
1.391 -The @command{ns-3} code relies heavily on
1.392 +The ns-3 code relies heavily on
1.393 @emph{Generalized Functors, Callbacks,
1.394 Smart Pointers, Singletons, and Object Factories}. Although we will
1.395 not assume any detailed knowledge of the idioms and design patterns used
1.396 -in the @command{ns-3}
1.397 +in the ns-3
1.398 system, it will be useful for readers who intend to delve deeply into the
1.399 system to understand some important related concepts. We recommend two
1.400 resources: @uref{http://www.amazon.com/Design-Patterns-Object-Oriented-Addison-Wesley-Professional/dp/0201633612/,,Design Patterns: Elements of Reusable Object-Oriented Software, Gamma et. al.} and
1.401 @uref{http://www.amazon.com/exec/obidos/ASIN/0201704315,,Modern C++ Design: Generic Programming and Design Patterns Applied, Alexandrescu}.
1.402
1.403 Gamma addresses the abstract design patterns, and Alexandrescu addresses the
1.404 -C++ idioms you will often see throughout the @command{ns-3} code.
1.405 +C++ idioms you will often see throughout the ns-3 code.
1.406
1.407 @cindex template
1.408 -Almost any use of @command{ns-3} will require some basic knowledge of C++
1.409 +Almost any use of ns-3 will require some basic knowledge of C++
1.410 templates.
1.411 We will discuss the high-level uses in this tutorial. However, if you venture
1.412 deeply into the source code, you will see fairly heavy use of relatively
1.413 sophisticated C++ templates in some of low-level modules of the system. The
1.414 You don't have to be a template guru to complete this tutorial but if you
1.415 -expect to work in @command{ns-3} at a low level you will have to be
1.416 +expect to work in ns-3 within the simulation core, you will have to be
1.417 somewhat fluent
1.418 with templates. If you want to truly grok C++ templates we recommend,
1.419 @uref{http://www.amazon.com/Templates-Complete-Guide-David-Vandevoorde/dp/0201734842/,,C++ Templates: The Complete Guide, Vandevoorde and Josuttis}.
1.420 @@ -322,11 +428,11 @@
1.421 that covers material you may need to understand for the multicast examples.
1.422
1.423 @c ========================================================================
1.424 -@c The Basics
1.425 +@c Downloading and Compiling
1.426 @c ========================================================================
1.427
1.428 -@node The-Basics
1.429 -@chapter The Basics
1.430 +@node Downloading and Compiling
1.431 +@chapter Downloading and Compiling
1.432
1.433 @cindex Linux
1.434 @cindex Cygwin
1.435 @@ -340,21 +446,21 @@
1.436 @cindex Waf
1.437 We are going to assume that you have Mercurial and Waf installed and running
1.438 on the target system as described in the Getting Started section of the
1.439 -@command{ns-3} web site: @uref{http://www.nsnam.org/getting_started.html}.
1.440 +ns-3 web site: @uref{http://www.nsnam.org/getting_started.html}.
1.441
1.442 @section Downloading
1.443 @cindex tarball
1.444 -The @command{ns-3} code is available in Mercurial repositories on the server
1.445 +The ns-3 code is available in Mercurial repositories on the server
1.446 code.nsnam.org. You can download a tarball, but we recommend working with
1.447 Mercurial --- it will make your life easier in the long run.
1.448
1.449 @cindex repository
1.450 If you go to the following link: @uref{http://code.nsnam.org/},
1.451 you will see a number of repositories. Many are the private repositories of
1.452 -the @command{ns-3} development team. The repositories of interest to you
1.453 +the ns-3 development team. The repositories of interest to you
1.454 will be
1.455 prefixed with ``ns-3''. The current development snapshot (unreleased) of
1.456 -@command{ns-3} may be found at: @uref{http://code.nsnam.org/ns-3-dev/}.
1.457 +ns-3 may be found at: @uref{http://code.nsnam.org/ns-3-dev/}.
1.458
1.459 The developers attempt to keep this repository in a consistent, working state
1.460 but it is a development area with unreleased code present, so you may want to
1.461 @@ -362,7 +468,7 @@
1.462
1.463 There will be a number of released repositories present at code.nsnam.org.
1.464 These repos will have names like ns-3.0.1 --- which referes to release 3.0.1
1.465 -of the network simulator (or if you like, release 0.1 of @command{ns-3}).
1.466 +of the network simulator (or if you like, release 0.1 of ns-3).
1.467 Since the releases are changing at a rate of one per month, I will stick with
1.468 the more constant ns-3-dev here, but you can replace the string ns-3-dev with
1.469 your choice of release (e.g., ns-3.0.5) below. You can find the latest
1.470 @@ -370,11 +476,12 @@
1.471 to the ``Getting Started'' web page and looking for the latest release
1.472 identifier.
1.473
1.474 -I typically create a directory called @code{repos} in my home directory under
1.475 -which I keep all of my local Mercurial repositories. @emph{Hint: I will
1.476 +One practice is to create a directory called @code{repos} in one's home
1.477 +directory under which one can keep local Mercurial repositories.
1.478 +@emph{Hint: we will
1.479 assume you do this later in the tutorial.} If you adopt that approach, you
1.480 -can get a copy of the development version of @command{ns-3} by typing
1.481 -the following into your Linux shell (I use bash).
1.482 +can get a copy of any of the development versions of ns-3 by typing
1.483 +the following into your Linux shell (assuming you have installed Mercurial):
1.484
1.485 @verbatim
1.486 cd
1.487 @@ -405,14 +512,14 @@
1.488 README doc/ samples/ utils/ wscript
1.489 @end verbatim
1.490
1.491 -You are now ready to build the @command{ns-3} distribution.
1.492 +You are now ready to build the ns-3 distribution.
1.493
1.494 @section Building
1.495 @cindex Waf!build
1.496 @cindex Waf!configure
1.497 @cindex Waf!debug
1.498 @cindex Waf!compile
1.499 -We use Waf to build the @command{ns-3} project. The first thing you
1.500 +We use Waf to build the ns-3 project. The first thing you
1.501 will need to do is to configure the build. For reasons that will become clear
1.502 later, we are going to work with debug builds in the tutorial. To explain to
1.503 Waf that it should do debug builds you will need to execute the following
1.504 @@ -452,10 +559,10 @@
1.505 @end verbatim
1.506
1.507 The build system is now configured and you can build the debug versions of
1.508 -the @command{ns-3} programs by simply typing,
1.509 +the ns-3 programs by simply typing,
1.510
1.511 @verbatim
1.512 - ./waf
1.513 + ./waf check
1.514 @end verbatim
1.515
1.516 You will see many Waf status messages displayed as the system compiles. The
1.517 @@ -465,12 +572,14 @@
1.518 Compilation finished successfully
1.519 @end verbatim
1.520
1.521 +and you will see a number of software unit tests subsequently execute.
1.522 +
1.523 @section Running a Script
1.524 @cindex Waf!run
1.525 We typically run scripts under the control of Waf. This allows the build
1.526 system to ensure that the shared library paths are set correctly and that
1.527 the libraries are available at run time. To run a program, simply use the
1.528 -@code{run} option in Waf. Let's run the @command{ns-3} equivalent of the hello
1.529 +@code{run} option in Waf. Let's run the ns-3 equivalent of the hello
1.530 world program by typing the following:
1.531
1.532 @verbatim
1.533 @@ -485,7 +594,10 @@
1.534 Hello Simulator
1.535 @end verbatim
1.536
1.537 -@emph{Congratulations. You are now an @command{ns-3} user.}
1.538 +If you want to run programs under another tool such as gdb or valgrind,
1.539 +see this @uref{http://www.nsnam.org/wiki/index.php/User_FAQ#How_to_run_NS-3_programs_under_another_tool,,wiki entry}.
1.540 +
1.541 +@emph{Congratulations. You are now an ns-3 user.}
1.542
1.543 @c ========================================================================
1.544 @c Some Prerequisites
1.545 @@ -502,19 +614,19 @@
1.546 @section Abstractions
1.547
1.548 In this section, we'll review some terms that are commonly used in
1.549 -networking, but have a specific meaning in @command{ns-3}.
1.550 +networking, but have a specific meaning in ns-3.
1.551
1.552 @subsection Node
1.553 @cindex Node
1.554 In Internet jargon, a computing device that connects to a network is called
1.555 -a @emph{host} or sometimes an @emph{end system}. Because @command{ns-3} is a
1.556 +a @emph{host} or sometimes an @emph{end system}. Because ns-3 is a
1.557 @emph{network} simulator, not specifically an @emph{Internet} simulator, we
1.558 intentionally do not use the term host since it is closely associated with
1.559 the Internet and its protocols. Instead, we use a more generic term also
1.560 used by other simulators that originates in Graph Theory --- the @emph{node}.
1.561
1.562 @cindex Node!class
1.563 -In @command{ns-3} the basic computing device abstraction is called the
1.564 +In ns-3 the basic computing device abstraction is called the
1.565 node. This abstraction is represented in C++ by the class @code{Node}. The
1.566 @code{Node} class provides methods for managing the representations of
1.567 computing devices in simulations. Developers are expected to specialize the
1.568 @@ -527,7 +639,7 @@
1.569 You should think of a @code{Node} as a computer to which you will add
1.570 functionality. One adds things like applications, protocol stacks and
1.571 peripheral cards with their associated drivers to enable the computer to do
1.572 -useful work. We use the same basic model in @command{ns-3}.
1.573 +useful work. We use the same basic model in ns-3.
1.574
1.575 @subsection Application
1.576 @cindex Application
1.577 @@ -542,14 +654,14 @@
1.578 @cindex system call
1.579 Often, the line of separation between system and application software is made
1.580 at the privilege level change that happens in operating system traps.
1.581 -In @command{ns-3} there is no real concept of operating system and especially
1.582 +In ns-3 there is no real concept of operating system and especially
1.583 no concept of privilege levels or system calls. We do, however, have the
1.584 idea of an application. Just as software applications run on computers to
1.585 -perform tasks in the ``real world,'' @command{ns-3} applications run on
1.586 -@command{ns-3} @code{Node}s to drive simulations in the simulated world.
1.587 +perform tasks in the ``real world,'' ns-3 applications run on
1.588 +ns-3 @code{Node}s to drive simulations in the simulated world.
1.589
1.590 @cindex Application!class
1.591 -In @command{ns-3} the basic abstraction for a user program that generates some
1.592 +In ns-3 the basic abstraction for a user program that generates some
1.593 activity to be simulated is the application. This abstraction is represented
1.594 in C++ by the class @code{Application}. The @code{Application} class provides
1.595 methods for managing the representations of our version of user-level
1.596 @@ -567,7 +679,7 @@
1.597 over which data flows in these netowrks are called @emph{channels}. When
1.598 you connect your Ethernet cable to the plug in the wall, you are connecting
1.599 your computer to an Ethernet communication channel. In the simulated world
1.600 -of @command{ns-3} one connects a @code{Node} to an object representing a
1.601 +of ns-3 one connects a @code{Node} to an object representing a
1.602 communication channel. Here the basic communication subnetwork abstraction
1.603 is called the channel and is represented in C++ by the class @code{Channel}.
1.604
1.605 @@ -602,7 +714,7 @@
1.606 collectively known as @emph{net devices}. In Unix and Linux you refer
1.607 to these net devices by names such as @emph{eth0}.
1.608
1.609 -In @command{ns-3} the @emph{net device} abstraction covers both the software
1.610 +In ns-3 the @emph{net device} abstraction covers both the software
1.611 driver and the simulated hardware. A net device is ``attached'' to a
1.612 @code{Node} in order to enable the @code{Node} to communicate with other
1.613 @code{Node}s in the simulation via @code{Channel}s. Just as in a real
1.614 @@ -619,13 +731,13 @@
1.615
1.616 @subsection Topology Helpers
1.617 In a real network, you will find host computers with added (or built-in)
1.618 -NICs. In @command{ns-3} we would say that you will find @code{Nodes} with
1.619 +NICs. In ns-3 we would say that you will find @code{Nodes} with
1.620 attached @code{NetDevices}. In a large simulated network you will need to
1.621 arrange many connections between @code{Node}s, @code{NetDevice}s and
1.622 @code{Channel}s.
1.623
1.624 Since connecting a @code{NetDevice} to a @code{Node}, and a @code{NetDevice}
1.625 -to a @code{Channel} is such a common task in @command{ns-3} we provide what we
1.626 +to a @code{Channel} is such a common task in ns-3 we provide what we
1.627 call @emph{topology helpers} to make this as easy as possible. Topology
1.628 helpers perform much of the dirty work of creating and connecting net devices.
1.629 For example, it may take several distinct method calls to create a NetDevice,
1.630 @@ -650,14 +762,14 @@
1.631 examine this in some detail here.
1.632
1.633 @cindex InternetNode
1.634 -@cindex Create
1.635 +@cindex CreateObject
1.636 @cindex Ptr
1.637 -In @command{ns-3}, if we want to create an @code{InternetNode} in a
1.638 +In ns-3, if we want to create an @code{InternetNode} in a
1.639 script, we will
1.640 typically do something like the following example:
1.641
1.642 @verbatim
1.643 - Ptr<Node> p = Create<InternetNode> ();
1.644 + Ptr<Node> p = CreateObject<InternetNode> ();
1.645 @end verbatim
1.646
1.647 @cindex smart pointer
1.648 @@ -677,7 +789,7 @@
1.649 using C++ @emph{templates}.
1.650
1.651 @verbatim
1.652 - Ptr<Node> p = Create<InternetNode> ();
1.653 + Ptr<Node> p = CreateObject<InternetNode> ();
1.654 @end verbatim
1.655
1.656 The purpose of templates is to allow a programmer to write one version of code
1.657 @@ -884,12 +996,12 @@
1.658 underlying data can be freed.
1.659
1.660 @cindex reference counting!intrusive
1.661 -The @command{ns-3} smart pointer mechanism uses a mechanism called intrusive
1.662 +The ns-3 smart pointer mechanism uses a mechanism called intrusive
1.663 reference counting to determine when a memory block should be automatically
1.664 deallocated. The term ``intrusive'' means that a reference count (a count of
1.665 variables required to have valid data) is stored in the object being managed
1.666 instead of in a proxy object. This means that each piece of memory managed by
1.667 -a @command{ns-3} smart pointer includes a reference count. When a smart
1.668 +a ns-3 smart pointer includes a reference count. When a smart
1.669 pointer to a reference counted object is created, this reference count is
1.670 incremented. This indicates that a new variable requires a valid data object
1.671 be present. When a smart pointer to a reference counted object is destroyed
1.672 @@ -916,7 +1028,7 @@
1.673 memory leaks.
1.674
1.675 Now, we want to make this feature available as widely as possible to objects
1.676 -in the @command{ns-3} system. The basic operations of the smart pointer class
1.677 +in the ns-3 system. The basic operations of the smart pointer class
1.678 are the same across any intrusively reference counted object. C++ provides a
1.679 mechanism to achieve this kind of generic behavior --- the template. Let's
1.680 examine the declaration of the smart pointer in more detail. First consider
1.681 @@ -955,21 +1067,21 @@
1.682 @end verbatim
1.683
1.684 @subsection Object Creation
1.685 -@cindex Create
1.686 +@cindex CreateObject
1.687 On the right hand side of the line of code we're examining (reproduced below
1.688 for convenience) is the creation of an @code{InternetNode} object.
1.689
1.690 @verbatim
1.691 - ... = Create<InternetNode> ();
1.692 + ... = CreateObject<InternetNode> ();
1.693 @end verbatim
1.694
1.695 @cindex template!function
1.696 This turns out to be an instance of use of a C++ @emph{function template}. The
1.697 -definition of the @code{Create<typename T>()} template calls the new operator
1.698 -to create an object of the type T. It then creates a new smart pointer of
1.699 -the appropriate type (i.e., @code{Ptr<T>}). This new smart pointer is
1.700 -assigned initial responsibility for the new object which has its reference
1.701 -count set to one.
1.702 +definition of the @code{CreateObject<typename T>()} template calls the new
1.703 +operator to create an object of the type T. It then creates a new smart
1.704 +pointer of the appropriate type (i.e., @code{Ptr<T>}). This new smart
1.705 +pointer is assigned initial responsibility for the new object which has its
1.706 +reference count set to one.
1.707
1.708 Since the underlying creation mechanism is via the @code{new} operator, and
1.709 you can pass parameters to the constructor for an object, we provide several
1.710 @@ -979,7 +1091,7 @@
1.711
1.712 @verbatim
1.713 int parm = 1;
1.714 - ... = Create<MyClass> (parm);
1.715 + ... = CreateObject<MyClass> (parm);
1.716 @end verbatim
1.717
1.718 We provide Create templates with up to seven parameters, so you could
1.719 @@ -987,7 +1099,7 @@
1.720
1.721 @verbatim
1.722 int parm = 1;
1.723 - ... = Create<MyClass> (p1, p2, p3, p4, p5, p6, p7);
1.724 + ... = CreateObject<MyClass> (p1, p2, p3, p4, p5, p6, p7);
1.725 @end verbatim
1.726
1.727 @subsection Type Safety
1.728 @@ -995,7 +1107,7 @@
1.729 have been examining for some time (again reproduced below).
1.730
1.731 @verbatim
1.732 - Ptr<Node> p = Create<InternetNode> ();
1.733 + Ptr<Node> p = CreateObject<InternetNode> ();
1.734 @end verbatim
1.735
1.736 @cindex smart pointer
1.737 @@ -1057,31 +1169,31 @@
1.738 to a base class happening in the assignment. That means that
1.739
1.740 @verbatim
1.741 - Ptr<Node> p = Create<InternetNode> ();
1.742 + Ptr<Node> p = CreateObject<InternetNode> ();
1.743 @end verbatim
1.744
1.745 or,
1.746
1.747 @verbatim
1.748 - Ptr<Channel> p = Create<CsmaChannel> ();
1.749 + Ptr<Channel> p = CreateObject<CsmaChannel> ();
1.750 @end verbatim
1.751
1.752 will work just fine. Of course, if you try something @emph{bad} (TM), like:
1.753
1.754 @verbatim
1.755 - Ptr<Node> p = Create<CsmaChannel> ();
1.756 + Ptr<Node> p = CreateObject<CsmaChannel> ();
1.757 @end verbatim
1.758
1.759 the compiler will quite appropriately complain that there is no conversion
1.760 between these completely unrelated objects (CsmaChannel and Node).
1.761
1.762 @subsection Summary
1.763 -Going back to our infamous first line of @command{ns-3} code, we said that if
1.764 +Going back to our infamous first line of ns-3 code, we said that if
1.765 we want to create an InternetNode in a script, we will typically do something
1.766 like:
1.767
1.768 @verbatim
1.769 - Ptr<Node> p = Create<InternetNode> ();
1.770 + Ptr<Node> p = CreateObject<InternetNode> ();
1.771 @end verbatim
1.772
1.773 @cindex Create
1.774 @@ -1106,9 +1218,9 @@
1.775 @chapter A First ns-3 script
1.776 @cindex design pattern
1.777 @cindex idiom
1.778 -Lets build a simple network using the @command{ns-3} design patterns, idioms,
1.779 +Lets build a simple network using the ns-3 design patterns, idioms,
1.780 classes and helpers we have just looked at. If you downloaded the system as
1.781 -was suggested above, you will have a release of @command{ns-3} in a directory
1.782 +was suggested above, you will have a release of ns-3 in a directory
1.783 called @code{repos} under your home directory. Change into that directory,
1.784 where you should see a directory structure something like the following.
1.785
1.786 @@ -1140,8 +1252,8 @@
1.787 }
1.788 @end verbatim
1.789
1.790 -This is the @command{ns-3} version of the ubiquitous hello-world program. It
1.791 -uses the @command{ns-3} Log module to print ``Hello Simulator'' into the
1.792 +This is the ns-3 version of the ubiquitous hello-world program. It
1.793 +uses the ns-3 Log module to print ``Hello Simulator'' into the
1.794 standard error output stream.
1.795
1.796 @cindex logging
1.797 @@ -1162,7 +1274,7 @@
1.798 @end verbatim
1.799
1.800 @cindex include files
1.801 -The @command{ns-3} build system places the core include files it needs into a
1.802 +The ns-3 build system places the core include files it needs into a
1.803 directory called @code{ns-3} and so whenever you need to include one of the
1.804 core files you need to explicitly code this. The file @code{ptr.h} defines
1.805 the generic smart pointer that we use. The file @code{internet-node.h}
1.806 @@ -1174,10 +1286,10 @@
1.807 after the call to @code{NS_LOG_INFO}.
1.808
1.809 @verbatim
1.810 - Ptr<Node> n0 = Create<InternetNode> ();
1.811 - Ptr<Node> n1 = Create<InternetNode> ();
1.812 - Ptr<Node> n2 = Create<InternetNode> ();
1.813 - Ptr<Node> n3 = Create<InternetNode> ();
1.814 + Ptr<Node> n0 = CreateObject<InternetNode> ();
1.815 + Ptr<Node> n1 = CreateObject<InternetNode> ();
1.816 + Ptr<Node> n2 = CreateObject<InternetNode> ();
1.817 + Ptr<Node> n3 = CreateObject<InternetNode> ();
1.818 @end verbatim
1.819
1.820 As we now understand, this will create four @code{InternetNode} objects on
1.821 @@ -1315,9 +1427,9 @@
1.822 similar to a multi-homed host. Each time you add a net device, you will get
1.823 a new index. Since the IP address for a multi-homed host is associated with
1.824 a net device, we need to provide that index (which we have saved) to the
1.825 -topology helper. We provide an IP version four address via the @command{ns-3}
1.826 +topology helper. We provide an IP version four address via the ns-3
1.827 class @code{Ipv4Address} which takes a dotted decimal string as a constructor
1.828 -parameter. We also provide a network mask using the @command{ns-3} class
1.829 +parameter. We also provide a network mask using the ns-3 class
1.830 @code{Ipv4Mask} which also takes a dotted decimal string. The code to
1.831 perform the IP address assignment, then, looks like the following:
1.832
1.833 @@ -1359,10 +1471,10 @@
1.834
1.835 NS_LOG_INFO ("Hello Simulator");
1.836
1.837 - Ptr<Node> n0 = Create<InternetNode> ();
1.838 - Ptr<Node> n1 = Create<InternetNode> ();
1.839 - Ptr<Node> n2 = Create<InternetNode> ();
1.840 - Ptr<Node> n3 = Create<InternetNode> ();
1.841 + Ptr<Node> n0 = CreateObject<InternetNode> ();
1.842 + Ptr<Node> n1 = CreateObject<InternetNode> ();
1.843 + Ptr<Node> n2 = CreateObject<InternetNode> ();
1.844 + Ptr<Node> n3 = CreateObject<InternetNode> ();
1.845
1.846 Ptr<CsmaChannel> lan =
1.847 CsmaTopology::CreateCsmaChannel (DataRate (5000000), MilliSeconds (2));
1.848 @@ -1398,9 +1510,9 @@
1.849
1.850 @section Using Applications
1.851 @cindex Create
1.852 -As mentioned above, we use @code{Application}s in @command{ns-3} to generate
1.853 +As mentioned above, we use @code{Application}s in ns-3 to generate
1.854 the data used to drive simulations. An @code{Application} is added to a
1.855 -@command{ns-3} node conceptually just as if you would add an application to a
1.856 +ns-3 node conceptually just as if you would add an application to a
1.857 computer. When an application is created (using the @code{Create} template)
1.858 we tell the application which @code{Node} it belongs to (and therefore on
1.859 which node it is running) by passing a smart pointer to that @code{Node} in
1.860 @@ -1423,8 +1535,8 @@
1.861 uint32_t maxPacketCount = 1;
1.862 Time interPacketInterval = Seconds (1.);
1.863
1.864 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n0, "10.1.1.2", port,
1.865 - maxPacketCount, interPacketInterval, packetSize);
1.866 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
1.867 + port, maxPacketCount, interPacketInterval, packetSize);
1.868 @end verbatim
1.869
1.870 @cindex packet
1.871 @@ -1466,7 +1578,7 @@
1.872 Ipv4Address addr ("10.1.1.2");
1.873 ...
1.874
1.875 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n0, addr, port,
1.876 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, addr, port,
1.877 maxPacketCount, interPacketInterval, packetSize);
1.878 @end verbatim
1.879
1.880 @@ -1474,7 +1586,7 @@
1.881 You can use the unnamed parameter idiom that we have previously seen:
1.882
1.883 @verbatim
1.884 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n0,
1.885 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0,
1.886 Ipv4Address ("10.1.1.2"), port, maxPacketCount, interPacketInterval,
1.887 packetSize);
1.888 @end verbatim
1.889 @@ -1482,12 +1594,12 @@
1.890 Or you can rely on implicit conversion sequences as we just saw:
1.891
1.892 @verbatim
1.893 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n0, "10.1.1.2", port,
1.894 - maxPacketCount, interPacketInterval, packetSize);
1.895 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
1.896 + port, maxPacketCount, interPacketInterval, packetSize);
1.897 @end verbatim
1.898
1.899 Which approach to take is a matter of style, really, and you will probably
1.900 -see all three approaches taken in the @command{ns-3} code. You should be
1.901 +see all three approaches taken in the ns-3 code. You should be
1.902 comfortable seeing and using all three methods.
1.903
1.904 @subsection A UDP Echo Server Application
1.905 @@ -1502,12 +1614,12 @@
1.906 following code:
1.907
1.908 @verbatim
1.909 - Ptr<UdpEchoServer> server = Create<UdpEchoServer> (n1, port);
1.910 + Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
1.911 @end verbatim
1.912
1.913 We only need to tell the application which node to reside on and which port
1.914 to listen on for UDP packets. The code to actually create the
1.915 -@code{UdpEchoServer} application uses the now quite familiar @command{ns-3} object
1.916 +@code{UdpEchoServer} application uses the now quite familiar ns-3 object
1.917 creation idiom.
1.918
1.919 @subsection A UDP Echo Client-Server Simulation
1.920 @@ -1538,10 +1650,10 @@
1.921
1.922 NS_LOG_INFO ("UDP Echo Simulation");
1.923
1.924 - Ptr<Node> n0 = Create<InternetNode> ();
1.925 - Ptr<Node> n1 = Create<InternetNode> ();
1.926 - Ptr<Node> n2 = Create<InternetNode> ();
1.927 - Ptr<Node> n3 = Create<InternetNode> ();
1.928 + Ptr<Node> n0 = CreateObject<InternetNode> ();
1.929 + Ptr<Node> n1 = CreateObject<InternetNode> ();
1.930 + Ptr<Node> n2 = CreateObject<InternetNode> ();
1.931 + Ptr<Node> n3 = CreateObject<InternetNode> ();
1.932
1.933 Ptr<CsmaChannel> lan =
1.934 CsmaTopology::CreateCsmaChannel (DataRate (5000000), MilliSeconds (2));
1.935 @@ -1575,10 +1687,10 @@
1.936 uint32_t maxPacketCount = 1;
1.937 Time interPacketInterval = Seconds (1.);
1.938
1.939 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n0, "10.1.1.2", port,
1.940 - maxPacketCount, interPacketInterval, packetSize);
1.941 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
1.942 + port, maxPacketCount, interPacketInterval, packetSize);
1.943
1.944 - Ptr<UdpEchoServer> server = Create<UdpEchoServer> (n1, port);
1.945 + Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
1.946
1.947 }
1.948 @end verbatim
1.949 @@ -1586,14 +1698,14 @@
1.950 @section Using the Simulation Engine
1.951 @cindex model
1.952 @cindex simulation executive
1.953 -You could say that the heart of the @command{ns-3} system is the
1.954 +You could say that the heart of the ns-3 system is the
1.955 @emph{simulation engine} (sometimes called the simulation executive in other
1.956 systems).
1.957
1.958 In a computer simulation, a computer @emph{model} of a real world @emph{system}
1.959 is constructed. This is typically done to minimize cost since you do not have
1.960 to actually buy, install and maintain physical hardware. In the case of
1.961 -@command{ns-3}, a model is a representation of a networking component that is
1.962 +ns-3, a model is a representation of a networking component that is
1.963 designed to imitate some number of important behaviors or characteristics of
1.964 an actual component in a real network. A system is a collection of models
1.965 arranged for the purpose of analyzing some behavior.
1.966 @@ -1604,7 +1716,7 @@
1.967 @cindex InternetNode
1.968 @cindex NIC
1.969 @cindex CSMA
1.970 -We have already encountered several @command{ns-3} models without specifically
1.971 +We have already encountered several ns-3 models without specifically
1.972 calling them so. The @code{InternetNode}, @code{CsmaNetDevice} and
1.973 @code{CsmaChannel} objects are models of an Internet computing node, a CSMA
1.974 network interface card (NIC), and a network cable able to move data to and
1.975 @@ -1624,7 +1736,7 @@
1.976 @cindex Ethernet
1.977 No model will fully implement @emph{all} of the behaviors of a piece of
1.978 hardware. It is important to understand what is being modeled by the
1.979 -@command{ns-3} components you are using and what is not. For example, the Csma
1.980 +ns-3 components you are using and what is not. For example, the Csma
1.981 components we use in this tutorial model a highly abstract multiple access
1.982 network that is topologically equivalent to an Ethernet. It is not necessarily
1.983 true that results found in a simulation using the Csma models will apply to
1.984 @@ -1661,7 +1773,7 @@
1.985 @cindex function object
1.986 @cindex callback
1.987 @cindex Callback
1.988 -In @command{ns-3} an event is basically a pre-packaged function call called a
1.989 +In ns-3 an event is basically a pre-packaged function call called a
1.990 @emph{functor}. Functors are also known as @emph{function objects}, which is
1.991 a more descriptive term --- an object (in the object-oriented programming
1.992 sense) that can be called as if it was a function. Typically one uses a
1.993 @@ -1673,9 +1785,9 @@
1.994 complete by calling some function you provide. This provided function is
1.995 known as a callback function. [Imagine calling someone on the telephone and
1.996 asking them to do something for you. You also ask them to @emph{call you back}
1.997 -when they are done.] Events in the @command{ns-3} system work conceptually
1.998 +when they are done.] Events in the ns-3 system work conceptually
1.999 the same way, except that instead of an I/O completion driving the process,
1.1000 -the arrival of some simulated time drives the process. The @command{ns-3}
1.1001 +the arrival of some simulated time drives the process. The ns-3
1.1002 deferred exectution mechanism is via a class called @code{Callback}.
1.1003
1.1004 @cindex Time
1.1005 @@ -1688,7 +1800,7 @@
1.1006 @section Driving the Simulation
1.1007 @cindex Application
1.1008 As mentioned previously, time is the driving force behind the progress of
1.1009 -a @command{ns-3} simulation. Events are scheduled to happen at certain times
1.1010 +a ns-3 simulation. Events are scheduled to happen at certain times
1.1011 by calling methods of the simulation engine, either directly or indirectly
1.1012 through, for example, an @code{Application}.
1.1013
1.1014 @@ -1738,7 +1850,7 @@
1.1015 you would attempt to start a client application in the real world.
1.1016
1.1017 @cindex socket!sendto
1.1018 -The @command{ns-3} equivalent of the call to @code{sendo} in the client will
1.1019 +The ns-3 equivalent of the call to @code{sendo} in the client will
1.1020 schedule (immediately) the transmission of a UDP packet over the just created
1.1021 socket. This will cause the packet to percolate down the protocol stack and
1.1022 eventually into the channel. The channel will schedule a reception event in
1.1023 @@ -1763,7 +1875,7 @@
1.1024 Simulator::Destroy ();
1.1025 @end verbatim
1.1026
1.1027 -We now have the makings of a complete @command{ns-3} network simulation. The
1.1028 +We now have the makings of a complete ns-3 network simulation. The
1.1029 source code for the script should look like the following:
1.1030
1.1031 @verbatim
1.1032 @@ -1792,10 +1904,10 @@
1.1033
1.1034 NS_LOG_INFO ("UDP Echo Simulation");
1.1035
1.1036 - Ptr<Node> n0 = Create<InternetNode> ();
1.1037 - Ptr<Node> n1 = Create<InternetNode> ();
1.1038 - Ptr<Node> n2 = Create<InternetNode> ();
1.1039 - Ptr<Node> n3 = Create<InternetNode> ();
1.1040 + Ptr<Node> n0 = CreateObject<InternetNode> ();
1.1041 + Ptr<Node> n1 = CreateObject<InternetNode> ();
1.1042 + Ptr<Node> n2 = CreateObject<InternetNode> ();
1.1043 + Ptr<Node> n3 = CreateObject<InternetNode> ();
1.1044
1.1045 Ptr<CsmaChannel> lan =
1.1046 CsmaTopology::CreateCsmaChannel (DataRate (5000000), MilliSeconds (2));
1.1047 @@ -1829,10 +1941,10 @@
1.1048 uint32_t maxPacketCount = 1;
1.1049 Time interPacketInterval = Seconds (1.);
1.1050
1.1051 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n0, "10.1.1.2", port,
1.1052 - maxPacketCount, interPacketInterval, packetSize);
1.1053 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
1.1054 + port, maxPacketCount, interPacketInterval, packetSize);
1.1055
1.1056 - Ptr<UdpEchoServer> server = Create<UdpEchoServer> (n1, port);
1.1057 + Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
1.1058
1.1059 server->Start(Seconds(1.));
1.1060 client->Start(Seconds(2.));
1.1061 @@ -1845,11 +1957,11 @@
1.1062 }
1.1063 @end verbatim
1.1064
1.1065 -@cindex csma-echo.cc
1.1066 +@cindex tutorial-csma-echo.cc
1.1067 Just to make sure you don't get caught up in debugging typographical errors
1.1068 we have provided this source code for you (along with a copyright header) in
1.1069 -the @code{tutorial} subdirectory of the @command{ns-3} distribution as
1.1070 -@code{csma-echo.cc}. We used this opportunity to do some ``clean up''
1.1071 +the @code{tutorial} subdirectory of the ns-3 distribution as
1.1072 +@code{tutorial-csma-echo.cc}. We used this opportunity to do some ``clean up''
1.1073 of some of our example cases by passing parameters using implicit conversion
1.1074 sequences and removing some of the named parameters. [These were used for
1.1075 pedagogic purposes and were not actually necessary.]
1.1076 @@ -1861,7 +1973,7 @@
1.1077 which is Python-based. We have to change gears slightly and switch ourselves
1.1078 to Python mode in order to proceed.
1.1079
1.1080 -In each subdirectory of the @command{ns-3} distribution in which there are
1.1081 +In each subdirectory of the ns-3 distribution in which there are
1.1082 source files, you will find two files: one will be named @code{waf} and one
1.1083 will be named @code{wscript}. The former, @code{waf}, is a link that allows
1.1084 one to start the build process from any subdirectory. We can ignore that one.
1.1085 @@ -1891,34 +2003,30 @@
1.1086
1.1087 All that needed to be done in order to build the new simulation using the new
1.1088 source file was to copy the two lines describing the @code{hello-simulator}
1.1089 -program and change the names to @code{csma-echo}. You can see these lines
1.1090 -in the @code{wscript} file,
1.1091 +program and change the names to @code{tutorial-csma-echo}. You can see these
1.1092 +lines in the @code{wscript} file,
1.1093
1.1094 @verbatim
1.1095 def build(bld):
1.1096 obj = bld.create_ns3_program('hello-simulator')
1.1097 obj.source = 'hello-simulator.cc'
1.1098
1.1099 - obj = bld.create_ns3_program('csma-echo')
1.1100 - obj.source = 'csma-echo.cc'
1.1101 + obj = bld.create_ns3_program('tutorial-csma-echo')
1.1102 + obj.source = 'tutorial-csma-echo.cc'
1.1103
1.1104 ...
1.1105 @end verbatim
1.1106
1.1107 When you built the system above, you actually already built this new
1.1108 simulation and a number of other examples. Since you have already configured
1.1109 -@code{Waf} and built the @code{csma-echo} script, you can run the simulation
1.1110 -in the same way as you ran the @code{hello-simulator} script using the
1.1111 -@code{waf --run} command:
1.1112 +@code{Waf} and built the @code{tutorial-csma-echo} script, you can run the
1.1113 +simulation in the same way as you ran the @code{hello-simulator} script using
1.1114 +the @code{waf --run} command:
1.1115
1.1116 @verbatim
1.1117 -~/repos/ns-3-dev/tutorial > waf --run csma-echo
1.1118 +~/repos/ns-3-dev/tutorial > waf --run tutorial-csma-echo
1.1119 Entering directory `~/repos/ns-3-dev/build'
1.1120 Compilation finished successfully
1.1121 UDP Echo Simulation
1.1122 ~/repos/ns-3-dev/tutorial >
1.1123 @end verbatim
1.1124 -
1.1125 -Wow! Wasn't that cool! I'm sure you can barely contain yourself at this
1.1126 -point. Okay, well, maybe we should figure out how to get some useful
1.1127 -information out of that simulation. It did run ... I promise.
2.1 --- a/doc/tutorial/other.texi Tue Feb 05 15:29:17 2008 -0500
2.2 +++ b/doc/tutorial/other.texi Tue Feb 05 15:30:16 2008 -0500
2.3 @@ -37,13 +37,13 @@
2.4 @center @image{pp,,,,png}
2.5
2.6 We have provided a file for you in the @code{tutorial}
2.7 -directory called @code{point-to-point.cc}. You should now be familiar enough
2.8 -with the system to pick out fairly easily what has been changed. Let's focus
2.9 -on the following lines:
2.10 +directory called @code{tutorial-point-to-point.cc}. You should now be
2.11 +familiar enough with the system to pick out fairly easily what has been
2.12 +changed. Let's focus on the following lines:
2.13
2.14 @verbatim
2.15 - Ptr<Node> n0 = Create<InternetNode> ();
2.16 - Ptr<Node> n1 = Create<InternetNode> ();
2.17 + Ptr<Node> n0 = CreateObject<InternetNode> ();
2.18 + Ptr<Node> n1 = CreateObject<InternetNode> ();
2.19
2.20 Ptr<PointToPointChannel> link = PointToPointTopology::AddPointToPointLink (
2.21 n0, n1, DataRate (38400), MilliSeconds (20));
2.22 @@ -79,7 +79,7 @@
2.23 to build and run this example and to locate and interpret the ASCII trace
2.24 file. This is left as an exercise for you.
2.25
2.26 -The file @code{point-to-point.cc} is reproduced here for your
2.27 +The file @code{tutorial-point-to-point.cc} is reproduced here for your
2.28 convenience:
2.29
2.30 @verbatim
2.31 @@ -132,8 +132,8 @@
2.32
2.33 NS_LOG_INFO ("Point to Point Topology Simulation");
2.34
2.35 - Ptr<Node> n0 = Create<InternetNode> ();
2.36 - Ptr<Node> n1 = Create<InternetNode> ();
2.37 + Ptr<Node> n0 = CreateObject<InternetNode> ();
2.38 + Ptr<Node> n1 = CreateObject<InternetNode> ();
2.39
2.40 Ptr<PointToPointChannel> link = PointToPointTopology::AddPointToPointLink (
2.41 n0, n1, DataRate (38400), MilliSeconds (20));
2.42 @@ -143,10 +143,10 @@
2.43
2.44 uint16_t port = 7;
2.45
2.46 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n0, "10.1.1.2", port,
2.47 - 1, Seconds(1.), 1024);
2.48 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
2.49 + port, 1, Seconds(1.), 1024);
2.50
2.51 - Ptr<UdpEchoServer> server = Create<UdpEchoServer> (n1, port);
2.52 + Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
2.53
2.54 server->Start(Seconds(1.));
2.55 client->Start(Seconds(2.));
2.56 @@ -167,7 +167,7 @@
2.57 A point-to-point network is considered a special case of a star network. As
2.58 you might expect, the process of constructing a star network is an extension
2.59 of the very simple process used for a point-to-point link. We have provided
2.60 -a file for you in the @code{tutorial} directory called @code{star.cc}
2.61 +a file for you in the @code{tutorial} directory called @code{tutorial-star.cc}
2.62 that implements a simple star network as seen below.
2.63
2.64 @sp 1
2.65 @@ -190,13 +190,13 @@
2.66 find and understand the code that creates these nodes.
2.67
2.68 @verbatim
2.69 - Ptr<Node> n0 = Create<InternetNode> ();
2.70 - Ptr<Node> n1 = Create<InternetNode> ();
2.71 - Ptr<Node> n2 = Create<InternetNode> ();
2.72 - Ptr<Node> n3 = Create<InternetNode> ();
2.73 - Ptr<Node> n4 = Create<InternetNode> ();
2.74 - Ptr<Node> n5 = Create<InternetNode> ();
2.75 - Ptr<Node> n6 = Create<InternetNode> ();
2.76 + Ptr<Node> n0 = CreateObject<InternetNode> ();
2.77 + Ptr<Node> n1 = CreateObject<InternetNode> ();
2.78 + Ptr<Node> n2 = CreateObject<InternetNode> ();
2.79 + Ptr<Node> n3 = CreateObject<InternetNode> ();
2.80 + Ptr<Node> n4 = CreateObject<InternetNode> ();
2.81 + Ptr<Node> n5 = CreateObject<InternetNode> ();
2.82 + Ptr<Node> n6 = CreateObject<InternetNode> ();
2.83 @end verbatim
2.84
2.85 Next, we get into the differences between the @code{PointToPointTopology}
2.86 @@ -290,7 +290,7 @@
2.87 to build and run this example and to locate and interpret the ASCII trace
2.88 file. This is left as an exercise for you.
2.89
2.90 -The file @code{star.cc} is reproduced here for your convenience:
2.91 +The file @code{tutorial-star.cc} is reproduced here for your convenience:
2.92
2.93 @verbatim
2.94 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2.95 @@ -345,13 +345,13 @@
2.96
2.97 NS_LOG_INFO ("Star Topology Simulation");
2.98
2.99 - Ptr<Node> n0 = Create<InternetNode> ();
2.100 - Ptr<Node> n1 = Create<InternetNode> ();
2.101 - Ptr<Node> n2 = Create<InternetNode> ();
2.102 - Ptr<Node> n3 = Create<InternetNode> ();
2.103 - Ptr<Node> n4 = Create<InternetNode> ();
2.104 - Ptr<Node> n5 = Create<InternetNode> ();
2.105 - Ptr<Node> n6 = Create<InternetNode> ();
2.106 + Ptr<Node> n0 = CreateObject<InternetNode> ();
2.107 + Ptr<Node> n1 = CreateObject<InternetNode> ();
2.108 + Ptr<Node> n2 = CreateObject<InternetNode> ();
2.109 + Ptr<Node> n3 = CreateObject<InternetNode> ();
2.110 + Ptr<Node> n4 = CreateObject<InternetNode> ();
2.111 + Ptr<Node> n5 = CreateObject<InternetNode> ();
2.112 + Ptr<Node> n6 = CreateObject<InternetNode> ();
2.113
2.114 Ptr<PointToPointChannel> link01 =
2.115 PointToPointIpv4Topology::CreateChannel (DataRate (38400),
2.116 @@ -439,10 +439,10 @@
2.117
2.118 uint16_t port = 7;
2.119
2.120 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n0, "10.1.1.2", port,
2.121 - 1, Seconds(1.), 1024);
2.122 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
2.123 + port, 1, Seconds(1.), 1024);
2.124
2.125 - Ptr<UdpEchoServer> server = Create<UdpEchoServer> (n1, port);
2.126 + Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
2.127
2.128 server->Start(Seconds(1.));
2.129 client->Start(Seconds(2.));
2.130 @@ -470,7 +470,7 @@
2.131 enable internetwork routing.
2.132
2.133 We have provided a file for you in the @code{tutorial} directory called
2.134 -@code{star-routing.cc} to show you how this is done. This extremely
2.135 +@code{tutorial-star-routing.cc} to show you how this is done. This extremely
2.136 tricky and difficult change is shown below:
2.137
2.138 @verbatim
2.139 @@ -483,11 +483,11 @@
2.140 We changed the client application so that it runs on node four:
2.141
2.142 @verbatim
2.143 - Ptr<UdpEchoClient> client = Create<UdpEchoClient> (n4, "10.1.1.2", port,
2.144 - 1, Seconds(1.), 1024);
2.145 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n4, "10.1.1.2",
2.146 + port, 1, Seconds(1.), 1024);
2.147 @end verbatim
2.148
2.149 -Now if you build and run @code{star-routing.cc} you can examine the
2.150 +Now if you build and run @code{tutorial-star-routing.cc} you can examine the
2.151 @code{tutorial.tr} file and see that your UDP echo packets are now correctly
2.152 routed through the topology.
2.153
2.154 @@ -508,7 +508,7 @@
2.155
2.156 We have provided a file that constructs this dumbbell network and creates
2.157 enough data flowing across the choke point that some packets will be dropped.
2.158 -The file is called @code{linear-dumbbell.cc} and is located in the
2.159 +The file is called @code{tutorial-linear-dumbbell.cc} and is located in the
2.160 @code{tutorial} directory. We have already covered all of the code used to
2.161 create this network, so we will just quickly go over the main sections of the
2.162 script.
2.163 @@ -521,10 +521,10 @@
2.164 //
2.165 // Create the lan on the left side of the dumbbell.
2.166 //
2.167 - Ptr<Node> n0 = Create<InternetNode> ();
2.168 - Ptr<Node> n1 = Create<InternetNode> ();
2.169 - Ptr<Node> n2 = Create<InternetNode> ();
2.170 - Ptr<Node> n3 = Create<InternetNode> ();
2.171 + Ptr<Node> n0 = CreateObject<InternetNode> ();
2.172 + Ptr<Node> n1 = CreateObject<InternetNode> ();
2.173 + Ptr<Node> n2 = CreateObject<InternetNode> ();
2.174 + Ptr<Node> n3 = CreateObject<InternetNode> ();
2.175
2.176 Ptr<CsmaChannel> lan1 =
2.177 CsmaTopology::CreateCsmaChannel (DataRate (10000000), MilliSeconds (2));
2.178 @@ -554,10 +554,10 @@
2.179 //
2.180 // Create the lan on the right side of the dumbbell.
2.181 //
2.182 - Ptr<Node> n4 = Create<InternetNode> ();
2.183 - Ptr<Node> n5 = Create<InternetNode> ();
2.184 - Ptr<Node> n6 = Create<InternetNode> ();
2.185 - Ptr<Node> n7 = Create<InternetNode> ();
2.186 + Ptr<Node> n4 = CreateObject<InternetNode> ();
2.187 + Ptr<Node> n5 = CreateObject<InternetNode> ();
2.188 + Ptr<Node> n6 = CreateObject<InternetNode> ();
2.189 + Ptr<Node> n7 = CreateObject<InternetNode> ();
2.190
2.191 Ptr<CsmaChannel> lan2 =
2.192 CsmaTopology::CreateCsmaChannel (DataRate (10000000), MilliSeconds (2));
2.193 @@ -615,19 +615,19 @@
2.194 //
2.195 uint16_t port = 7;
2.196
2.197 - Ptr<UdpEchoClient> client0 = Create<UdpEchoClient> (n0, "10.1.2.1", port,
2.198 - 100, Seconds(.01), 1024);
2.199 - Ptr<UdpEchoClient> client1 = Create<UdpEchoClient> (n1, "10.1.2.2", port,
2.200 - 100, Seconds(.01), 1024);
2.201 - Ptr<UdpEchoClient> client2 = Create<UdpEchoClient> (n2, "10.1.2.3", port,
2.202 - 100, Seconds(.01), 1024);
2.203 - Ptr<UdpEchoClient> client3 = Create<UdpEchoClient> (n3, "10.1.2.4", port,
2.204 - 100, Seconds(.01), 1024);
2.205 + Ptr<UdpEchoClient> client0 = CreateObject<UdpEchoClient> (n0, "10.1.2.1",
2.206 + port, 100, Seconds(.01), 1024);
2.207 + Ptr<UdpEchoClient> client1 = CreateObject<UdpEchoClient> (n1, "10.1.2.2",
2.208 + port, 100, Seconds(.01), 1024);
2.209 + Ptr<UdpEchoClient> client2 = CreateObject<UdpEchoClient> (n2, "10.1.2.3",
2.210 + port, 100, Seconds(.01), 1024);
2.211 + Ptr<UdpEchoClient> client3 = CreateObject<UdpEchoClient> (n3, "10.1.2.4",
2.212 + port, 100, Seconds(.01), 1024);
2.213
2.214 - Ptr<UdpEchoServer> server4 = Create<UdpEchoServer> (n4, port);
2.215 - Ptr<UdpEchoServer> server5 = Create<UdpEchoServer> (n5, port);
2.216 - Ptr<UdpEchoServer> server6 = Create<UdpEchoServer> (n6, port);
2.217 - Ptr<UdpEchoServer> server7 = Create<UdpEchoServer> (n7, port);
2.218 + Ptr<UdpEchoServer> server4 = CreateObject<UdpEchoServer> (n4, port);
2.219 + Ptr<UdpEchoServer> server5 = CreateObject<UdpEchoServer> (n5, port);
2.220 + Ptr<UdpEchoServer> server6 = CreateObject<UdpEchoServer> (n6, port);
2.221 + Ptr<UdpEchoServer> server7 = CreateObject<UdpEchoServer> (n7, port);
2.222
2.223 server4->Start(Seconds(1.));
2.224 server5->Start(Seconds(1.));
2.225 @@ -651,10 +651,10 @@
2.226 @end verbatim
2.227
2.228 The remainder of the file should be quite familiar to you. Go ahead and
2.229 -run @code{linear-dumbbell}. Now take a look at the trace (@code{tutorial.tr})
2.230 -file. You will now see trace lines that begin with @code{d}. Alternatively
2.231 -you can search for the string ``queue-drop'' which is the expansion of the
2.232 -drop code.
2.233 +run @code{tutorial-linear-dumbbell}. Now take a look at the trace
2.234 +(@code{tutorial.tr}) file. You will now see trace lines that begin with
2.235 +@code{d}. Alternatively you can search for the string ``queue-drop'' which
2.236 +is the expansion of the drop code ('d').
2.237
2.238 Interpretation of a dropped packet is straightforward. We have expanded
2.239 the first @code{queue-drop} trace for you below. See the section on ASCII
2.240 @@ -699,7 +699,7 @@
2.241 We have written a number of @command{ns-3} scripts in C++. Although we have
2.242 been perfectly linear in our script implementations, just like any other C++
2.243 program, an @command{ns-3} script can use any features of the language you
2.244 -desire. If you will look back at the @code{linear-dumbbell.cc}
2.245 +desire. If you will look back at the @code{tutorial-linear-dumbbell.cc}
2.246 example, you may notice that the code to create the left and right sides of
2.247 the dumbbell is operationally identical --- only the names change. An obvious
2.248 improvement of this program would be to use subroutines to create the sides.
2.249 @@ -841,12 +841,12 @@
2.250 @end verbatim
2.251
2.252 That's it. We have actually already walked through almost all of the code
2.253 -required to construct a bus network in our @code{csma-echo.cc}
2.254 +required to construct a bus network in our @code{tutorial-csma-echo.cc}
2.255 example, so let's just jump forward and take a look at an implementation
2.256 of this thing. We provide an implementation for you in the files
2.257 @code{ipv4-bus-network.h} and @code{ipv4-bus-network.cc} located in the
2.258 @code{tutorial} directory. We also provide an example that uses the new
2.259 -class in the file @code{bus-network.cc}.
2.260 +class in the file @code{tutorial-bus-network.cc}.
2.261
2.262 The interesting method from our current perspective is the Ipv4BusNetwork
2.263 constructor, shown below:
2.264 @@ -869,7 +869,7 @@
2.265
2.266 for (uint32_t i = 0; i < n; ++i)
2.267 {
2.268 - Ptr<Node> node = Create<InternetNode> ();
2.269 + Ptr<Node> node = CreateObject<InternetNode> ();
2.270 uint32_t nd = CsmaIpv4Topology::AddIpv4CsmaNetDevice (node, m_channel,
2.271 Mac48Address::Allocate ());
2.272 Ipv4Address address = Ipv4AddressGenerator::AllocateAddress (mask,
2.273 @@ -978,7 +978,7 @@
2.274
2.275 for (uint32_t i = 0; i < n; ++i)
2.276 {
2.277 - Ptr<Node> node = Create<InternetNode> ();
2.278 + Ptr<Node> node = CreateObject<InternetNode> ();
2.279 uint32_t nd = CsmaIpv4Topology::AddIpv4CsmaNetDevice (node, m_channel,
2.280 Mac48Address::Allocate ());
2.281 Ipv4Address address = Ipv4AddressGenerator::AllocateAddress (mask,
2.282 @@ -1093,9 +1093,10 @@
2.283
2.284 The @command{ns-3} object model takes the C++ language (system level) object
2.285 model as its basis, and extends that model by providing an API for software
2.286 -componentry. You will find terms like Component, Interface and QueryInterface
2.287 -in the following discussion. It is important to understand from the outset
2.288 -that this is the @command{ns-3} object model, and not any other object model.
2.289 +componentry. You may find terms like Component, Interface and QueryInterface
2.290 +in the following discussion, or used informally in other discussions about
2.291 +@command{ns-3}. It is important to understand from the outset that this is
2.292 +the @command{ns-3} object model, and not any other object model.
2.293 Richard Feynman (an American physicist) once described the behavior of matter
2.294 and light on a very small scale in the following way,
2.295
2.296 @@ -1111,7 +1112,7 @@
2.297 software componentry before continuing. To paraphrase Feynman, @command{ns-3}
2.298 components do not behave like COM Components, or Java Beans, or CORBA
2.299 objects, or clouds or weights on springs, or like anything that you have
2.300 -ever seen they are @command{ns-3} components.
2.301 +ever seen --- they are @command{ns-3} components.
2.302
2.303 @section The C++ Object Model is the Root of all Things
2.304 @command{Ns-3} is primarily a C++ system. The system is written in C++ and
2.305 @@ -1125,7 +1126,7 @@
2.306 @code{Create} as in the following example:
2.307
2.308 @verbatim
2.309 - Ptr<Node> n0 = Create<InternetNode> ();
2.310 + Ptr<Node> n0 = CreateObject<InternetNode> ();
2.311 @end verbatim
2.312
2.313 This line of code, while it may be unfamiliar to some, is pure C++. If you
2.314 @@ -1180,7 +1181,7 @@
2.315
2.316 @section Interfaces
2.317 There are many different ideas floating around of what exactly the term
2.318 -@emph{Interface} means. Originally an interface just meant a communication
2.319 +@emph{interface} means. Originally an interface just meant a communication
2.320 boundary between two entities. As the concepts of object oriented programming
2.321 (OOP) were surfacing in the 1980s, the term interface was applied to the
2.322 collection of access methods for the modular entities that were being defined.
2.323 @@ -1216,21 +1217,22 @@
2.324 When we speak of an ns-3 interface, we do not worry about interface definition
2.325 languages, or pure virtual classes, or registries we just think about C++
2.326 object declarations and their associated methods. When we instantiate an
2.327 -@command{ns-3} Interface, it is the C++ object model that dictates how that
2.328 +@command{ns-3} interface, it is the C++ object model that dictates how that
2.329 object is brought into existence. When a method is called on an @command{ns-3}
2.330 Interface, it is the C++ object model that dictates how that method is
2.331 dispatched.
2.332
2.333 -The only difference between a vanilla C++ object and an ns-3 Interface, is
2.334 -that an object acting as an ns-3 Interface must inherit from the base class
2.335 -Object. This inheritance gives the Interface object a very useful capability.
2.336 +The only difference between a vanilla C++ object and an ns-3 object with a
2.337 +specifically defined interface, is that an object acting as an ns-3 interface
2.338 + must inherit from the base class Object. This inheritance gives the Object
2.339 +a very useful capability conceptually similar to a COM Interface.
2.340
2.341 -@section The Ns-3 Capital I Interface and QueryInterface
2.342 -One thing that Microsoft got right in the Component Object Model was the idea
2.343 -of Interface aggregation and discovery via QueryInterface. We have embraced
2.344 -these ideas in @command{ns-3}. This was done primarily to address a common
2.345 -problem in large software systems. A good example of this problem happens
2.346 -in the @command{ns-3} Node class.
2.347 +@section The Ns-3 Interface and GetObject
2.348 +One thing that Microsoft arguably got right in the Component Object Model was
2.349 +the idea of Interface aggregation and discovery via QueryInterface. We have
2.350 +embraced these ideas in @command{ns-3}. This was done primarily to address a
2.351 +common problem in large software systems. A good example of this problem
2.352 +happens in the @command{ns-3} Node class.
2.353
2.354 If one were to take the standard OOP view of specializing a @code{Node} into
2.355 an internet host, for example, one would typically inherit from the @code{Node}
2.356 @@ -1284,570 +1286,789 @@
2.357
2.358 Composition, usually called @emph{aggregation}, along with runtime Interface
2.359 discovery is the solution that Microsoft originally championed and that
2.360 -@command{ns-3} has adopted. In our example a @code{Node} would contain
2.361 -separate Interface objects implementing internetwork routing and TCP/IP.
2.362 -These contained objects have interfaces in the C++ sense of collections of
2.363 -method signatures. When objects are capable of participating in this
2.364 -aggregation process, they are called @command{ns-3} Interfaces and they
2.365 -receive the functionality required for this participation by inheriting
2.366 -from the base class @code{Object}.
2.367 +@command{ns-3} has adopted --- albeit with many simplifications and a few name
2.368 +changes.
2.369
2.370 -@subsection Object, interfaces and Interfaces
2.371 -As mentioned above, the class that implements the aggregation mechanism for
2.372 -@command{ns-3} objects is called @code{Object}. The class named @code{Object}
2.373 -is simply a base class that you will inherit from if you want your objects
2.374 -to support aggregation and QueryInterface. Many systems have a base class
2.375 -that implements common functionality and these base classes are typically
2.376 -called Object. The @command{ns-3} version of this object base class relates
2.377 -primarily to Interface aggregation, although it does provide methods to help
2.378 -with intrusive reference counting and tracing as well.
2.379 +@subsection Objects and Interfaces
2.380 +Now that we have mentioned Microsoft COM and are almost obligated to mention
2.381 +the terms Interface and QueryInterface. For those familiar with COM, loosely
2.382 +speaking, QueryInterface is to COM as GetObject is to @command{ns-3}.
2.383 +The analogy, while good conceptually, is superficial from an implementation
2.384 +point of view.
2.385 +
2.386 +Addressing our current example of a @code{Node}, generically speaking, each
2.387 +node needs to aggregate an object that will implement internetwork routing
2.388 +and TCP/IP. The system will need to provide a mechanism for locating the
2.389 +aggregated objects and allow a client to discover them.
2.390 +
2.391 +These aggregated objects have interfaces in the C++ sense of collections of
2.392 +method signatures. In @command{ns-3}, when objects are capable of
2.393 +participating in this aggregation process, they are called @command{ns-3}
2.394 +@code{Objects}. @code{Object}s receive the functionality required for this
2.395 + participation by inheriting from the @command{ns-3} base class @code{Object}.
2.396 +
2.397 +Note well that when we write the word @code{Object} (note the uppercase 'O' in
2.398 +the spelling and the change of font) we are referring to a kind of C++ object
2.399 +that has inherited the capability of participating in an aggregation. The
2.400 +@command{ns-3}-specific word @code{Object} can have a significantly different
2.401 +meaning than that of a vanilla C++ object outside the aforementioned
2.402 +inheritance tree, and the difference is only readily apparent via context.
2.403 +In this tutorial we will always write the @command{ns-3}-specific kind of
2.404 +@code{Object} in a fixed font; and will write the vanilla C++ term object in
2.405 +normal font. In conversation, you will need to be careful to understand which
2.406 +term is meant: object or @code{Object}.
2.407 +
2.408 +Once an object has inherited from class @code{Object} it has the ability to
2.409 +@emph{host} an aggregation. This means that it has the ability to add other
2.410 +@code{Objects} to its aggregation via the method @code{AggregateObject}. It
2.411 +also means that it can provide a service to @emph{discover} other objects in
2.412 +its aggregation via the method @code{GetObject}.
2.413 +
2.414 +
2.415 +Technically, the class named @code{Object} is simply a base class that you
2.416 +will inherit from if you want your @code{Objects} to support aggregation and
2.417 +discovery. Many systems have a base class that implements common
2.418 +functionality and these base classes are typically called somthing like
2.419 +Object. The @command{ns-3} version of this base class relates primarily to
2.420 +@code{Object} aggregation and discovery, although it does also provide methods
2.421 +to help with intrusive reference counting and tracing as well.
2.422
2.423 When a C++ object inherits from the ns-3 Object base class, it is conceptually
2.424 -promoted to an ns-3 Interface (note the capital I in Interface) irrespective
2.425 -of how the object was declared (e.g., as an abstract base class, concrete
2.426 -class, with virtual methods, etc.). In ns-3, you should associate
2.427 -inheritance from the class named @code{Object} with promotion of an object to
2.428 -the status of Interface rather than the form of the Interface declaration.
2.429 +promoted to an ns-3 @code{Object} irrespective of how the object was declared
2.430 +(e.g., as an abstract base class, concrete class, with virtual methods, etc.).
2.431 +In ns-3, you should associate inheritance from the class named @code{Object}
2.432 +with promotion of an object to the status of some locatable @code{Object}
2.433 +rather than with the form of the class declaration.
2.434
2.435 -When you inherit from @code{Object}, you will get new methods and an
2.436 -Interface Identifier. The Interface Identifer, or @emph{iid}, is the
2.437 -@command{ns-3} version of the @emph{Universally Unique ID} (UUID) or
2.438 -@emph{Globally Unique ID} (GUID) found in other systems. Unlike the GUID, it
2.439 -is really a dynamically created process-local ID. For now, consider it as
2.440 -simply a number which the system will generate for you that uniquely
2.441 -identifies an Interface class within the ns-3 system and allows you to
2.442 -specify an interface type to @code{QueryInterface}.
2.443 +For those of you unfamiliar with Microsoft COM, CORBA or ORBit, this might
2.444 +sound obvious. For those of with such a background, the point we are making
2.445 +is that there is no such thing in @command{ns-3} as a separate Interface
2.446 +declaration, no such thing as an Interface Definiition Language, no such thing
2.447 +as a UUID or GUID, etc. In @command{ns-3} we just work with C++ objects that
2.448 +may be given some very useful abilities by inheriting from the @command{ns-3}
2.449 +base class @code{Object}. @command{Ns-3} @code{Object}s are not required to
2.450 +inherit from classes composed of pure virtual methods in order to define an
2.451 +Interface. It's all really just ``plain old C++.''
2.452
2.453 To summarize, when you instantiate an object that inherits from the
2.454 @code{Object} class, you will have a C++ object that has four important
2.455 properties:
2.456
2.457 @itemize @bullet
2.458 -@item The object has a C++ interface defined by the collection of method signatures in its inheritance tree;
2.459 -@item The object has an Interface ID that uniquely identifies the C++ interface of its class;
2.460 -@item The object is a container that has the ability to aggregate other interfaces;
2.461 -@item The object exports a method that allows for discovery of aggregated interfaces (@code{QueryInterface}) according to Interface ID.
2.462 +@item The @code{Object} has a C++ interface defined by the collection of method signatures in its inheritance tree;
2.463 +@item The @code{Object} has some way to identify its underlying class uniquely;
2.464 +@item The @code{Object} is a kind of container that has the ability to aggregate other @code{Object}s using the method @code{AggregateObject};
2.465 +@item The @code{Object} exports a method called @code{GetObject} that allows for discovery of other aggregated @code{Object}s.
2.466 @end itemize
2.467
2.468 -It is crucially important to understand what we have described here. A given
2.469 -C++ class has an object access interface that is essentially the collection
2.470 -of method signatures specified in its inheritance tree. This is a C++ object
2.471 -model thing. Ns-3 provides a base class from which the class in question can
2.472 -inherit and be promoted to the status of Interface. Once a class becomes
2.473 -an Interface it has inherited the ability to set its own interface identifier
2.474 -(@code{iid}), and exports methods to aggregate and search other Interfaces
2.475 -that are added to its aggregation.
2.476 +It is crucially important to understand what we have described here
2.477 +(especially for those coming from other systems that provide similar
2.478 +functionality). A given C++ class has an object access interface that is
2.479 +essentially the collection of method signatures specified in its inheritance
2.480 +tree. This is a C++ object model thing. Ns-3 provides a base class from
2.481 +which the class in question can inherit and be promoted to the status of
2.482 +@code{Object}. Once a class becomes an @code{Object} it has inherited the
2.483 +ability to aggregate and search for other @code{Objects} that are added to
2.484 +its aggregation.
2.485
2.486 -That last detail is important. In @command{ns-3} Interfaces are both
2.487 -containers and specifications for object method access. We have previously
2.488 -mentioned the @code{Node} class acts as a container. In fact, the @code{Node}
2.489 -class inherits from @code{Object} and is itself also an @command{ns-3}
2.490 -Interface. When the @code{Node} object is created it is really an aggregation
2.491 -of one Interface, the @code{Node} Interface. This is generally true ---
2.492 -Interfaces are both containers and Interfaces.
2.493 +That last detail is important. In @command{ns-3} @code{Object}s are both
2.494 +containers and specifications for a object method access. We have previously
2.495 +mentioned that the @code{Node} class acts as a container. In fact, the
2.496 +@code{Node} class inherits from @code{Object} and is itself an @command{ns-3}
2.497 +@code{Object}. So, when the @code{Node} object is created it is really an
2.498 +aggregation of one @code{Object} and you can call @code{AggregateObject} or
2.499 +@code{GetObject} on the resulting @code{Node} object. Along with being an
2.500 +aggregation, the @code{Node} class also describes a public interface. THis
2.501 +public interface (API) is declared just as any C++ object is declared, via its
2.502 +class methods as specified in the inheritance tree. For those steeped in
2.503 +COM or CORBA, this is where the concept of Interface works in @command{ns-3}.
2.504 +Remember that it is generally true that @code{Object}s are both aggregations
2.505 +and APIs.
2.506
2.507 @subsection Aggregations
2.508 -The figure below shows how an Interface could be illustrated in detail. The
2.509 -line with the circle at the top of the diagram represents the appearance of the
2.510 -Interface to the external world. This circle and line are called a lollipop
2.511 -because of its superficial similarity to a kind of childs candy.
2.512 +The figure below shows how an @code{Object} could be illustrated in detail.
2.513 +The line with the circle at the top of the diagram represents the appearance
2.514 +of the @code{Object} API to the external world. This circle and line are
2.515 +together called a lollipop because of its superficial similarity to a kind of
2.516 +childs candy.
2.517
2.518 @sp 1
2.519 @center @image{oneif,,,,png}
2.520
2.521 -You could declare this interface quite simply using a non-virtual class as
2.522 -follows,
2.523 +You could declare this API and associated @code{Object} quite simply using a
2.524 +non-virtual class as follows,
2.525
2.526 @verbatim
2.527 class A : public Object {
2.528 public:
2.529 - static const InterfaceId iid;
2.530 + static ns3::TypeId GetTypeId (void)
2.531 + {
2.532 + static ns3::TypeId tid = ns3::TypeId ("A")
2.533 + .SetParent (Object::GetTypeId ())
2.534 + .AddConstructor<A> ();
2.535 + return tid;
2.536 + }
2.537 +
2.538 + A ()
2.539 + {
2.540 + }
2.541 +
2.542 void MethodA (void);
2.543 };
2.544 @end verbatim
2.545
2.546 The methods that are then available via the Interface labeled @code{A} in the
2.547 -figure above are the methods inherited from the @code{Object} base class (
2.548 -@code{QueryInterface}, @code{Ref}, and @code{Unref}) and those from class
2.549 -@code{A} (@code{MethodA}). Note that you must declare an @code{InterfaceId}
2.550 -for your Interface class, and it must be declared static to make it class-wide
2.551 -in scope. This @code{iid} can be thought of as a kind of type information
2.552 -that uniquely identifies objects as being instantiated from this class.
2.553 +figure above are the methods inherited from the @code{Object} base class
2.554 +(@code{GetObject}, @code{Ref}, and @code{Unref}) and those from class
2.555 +@code{A} (@code{MethodA}).
2.556
2.557 -You can think of the arc and arrow device coming off each side of the
2.558 -Interface as part of a connector. These connectors allow @code{QueryInterface}
2.559 -to search aggregations for a particular @code{iid}. The figure below shows an
2.560 -aggregation of three Interfaces: A, B and C. The class declarations for
2.561 -classes @code{B} and @code{C} are substantially similar to that of class
2.562 -@code{A}.
2.563 +Note that you must declare a @code{TypeId} in your @code{Object} class, and
2.564 +it must be declared static to make it class-wide in scope. This @code{TypeId}
2.565 +is a unifying element in the @command{ns-3} object model and uniquely
2.566 +identifies @code{Objects} at run-time as being instantiated from a particular
2.567 +class. We'll have much more to say about @code{TypiId} shortly.
2.568 +
2.569 +You can think of the arc and arrow device coming off each side of the
2.570 +illustrated @code{Object}s as part of a connector. These connectors allow
2.571 +@code{GetObject} to search aggregations for an instance of a class type.
2.572 +The figure below shows an aggregation of three @code{Object}s: A, B and C.
2.573 +The class declarations for classes @code{B} and @code{C} are substantially
2.574 +similar to that of class @code{A}.
2.575
2.576 @sp 1
2.577 @center @image{threeif,,,,png}
2.578
2.579 -You can visualize these Interfaces as being snapped together like Lego
2.580 -building blocks if you like. When the Interfaces are aggregated, a
2.581 -@code{QueryInterface} search path is formed through the connectors. In order
2.582 -to create this aggregation we first need to create the Interface objects.
2.583 +You can visualize these @code{Object}s as being snapped together like Lego
2.584 +building blocks if you like. When @code{Object}s are aggregated, a
2.585 +@code{GetObject} search path is formed through the connectors. In order
2.586 +to create this aggregation you will first need to create the Interface objects.
2.587 These are just normal, everyday C++ objects that we can create using the
2.588 -@code{Create} template function and manage using smart pointers. The
2.589 +@code{CreateObject} template function and manage using smart pointers. The
2.590 following code should be obvious to you by now:
2.591
2.592 @verbatim
2.593 - Ptr<A> a = Create<A> ();
2.594 - Ptr<B> b = Create<B> ();
2.595 - Ptr<C> c = Create<C> ();
2.596 + Ptr<A> a = CreateObject<A> ();
2.597 + Ptr<B> b = CreateObject<B> ();
2.598 + Ptr<C> c = CreateObject<C> ();
2.599 @end verbatim
2.600
2.601 -When you create an aggregation, you pick one of the Interfaces to act as
2.602 -the container. In this case well pick Interface A. In order to aggregate
2.603 -an Interface, you simply call the method @code{AddInterface} that your class
2.604 -inherited from @code{Object}. The following code will aggregate Interface
2.605 -@code{B} and Interface @code{C} onto the Interface (and container) @code{A}.
2.606 +When you create an aggregation, you pick one of the @code{Object}s of the
2.607 +aggregation to think of as the container. In this case well pick @code{Object}
2.608 +A. In order to aggregate an @code{Object}, you simply call the method
2.609 +@code{AggregateObject} that your class has inherited from class @code{Object}.
2.610 +The following code will aggregate @code{Object B} and @code{Object C} onto
2.611 +the @code{Object} (and container/aggregation) @code{A}.
2.612
2.613 @verbatim
2.614 - a->AddInterface (b);
2.615 - a->AddInterface (c);
2.616 + a->AggregateObject (b);
2.617 + a->AggregateObject (c);
2.618 @end verbatim
2.619
2.620 Thats all there is to it. Now that you have those connectors snapped
2.621 -together, you can ask each of the Interfaces in the aggregation for any of
2.622 -the Interfaces in the aggregation. Lets look at a simple example:
2.623 +together, you can ask each of the @code{Object}s in the aggregation for any of
2.624 +the other @code{Object}s in the aggregation. Lets look at a simple example:
2.625
2.626 @verbatim
2.627 - Ptr<B> newB = a->QueryInterface<B> (B:iid);
2.628 + Ptr<B> newB = a->GetObject<B> ();
2.629 @end verbatim
2.630
2.631 -The left hand side of this assignment declares a smart pointer to the class
2.632 -@code{B} to help with memory management of the returned Interface pointer.
2.633 -Object lifetime management is very important when dealing with Interfaces
2.634 -and our smart pointer will simply take care of it all for you.
2.635 +Now, the explanation of what this snippet does is not as simple as writing it.
2.636 +The left hand side of this assignment declares a smart pointer to the class
2.637 +@code{B} to help with memory management of the returned @code{Object} pointer.
2.638 +You should be very familiar with smart pointers at this stage of the tutorial.
2.639
2.640 -The right hand side illustrates the basic idea of @code{QueryInterface}. We
2.641 -take a take a (smart) pointer to Interface @code{A} and ask it to search the
2.642 -aggregation for an interface associated with an interface identifier with
2.643 -the value of @code{B:iid} which is passed as a parameter. Recall that
2.644 -@code{B::iid} is the @code{static InterfaceId} of the Interface class
2.645 -@code{B}. Observe that @code{QueryInterface} is a template function and the
2.646 -type specified in the angle brackets, here @code{<B>}, tells it what kind of
2.647 -smart pointer to return. In this case @code{QueryInterface} will find an
2.648 -Interface object of type @code{B::iid} in its list of Interfaces and return a
2.649 -smart pointer to @code{B} as instructed.
2.650 +The right hand side illustrates how @code{GetObject} is acutally used.
2.651 +The method @code{GetObject} is templated. The assocated template parameter
2.652 +(between the brackets) specifies the @emph{class} that is being requested.
2.653 +This is important. Since it is the class type that specifies the search
2.654 +criteron, there can be only one instance of a particular class present in an
2.655 +aggregation. Looking back a little, although the parameter to
2.656 +@code{AggregateObject} appears to be a vanilla C++ object (@code{b} or @code{c}
2.657 +above), it actually represents (is an instance of) a class that has an
2.658 +associated @code{TypeId} and inherits from @code{Object}. When you call
2.659 +@code{GetObject} you specify the search criterion (using the template
2.660 +parameter) as a class name. This referenced class must also have an
2.661 +associated @code{TypeId} and must also have inherited from @code{Object}.
2.662
2.663 -Now that you have those connectors snapped together, you can ask each of
2.664 -the Interfaces in the aggregation for any of the Interfaces in the
2.665 -aggregation. For example we could walk the Interfaces asking each for the
2.666 -next in the aggregation. First we would ask the Interface pointed to by the
2.667 -smart pointer a to look for the InterfaceId representing @code{B}:
2.668 +This may be summarized by saying that @code{AggregateObject} takes an
2.669 +@emph{instance} of an object of a particular class that inherits from
2.670 +@code{Object}. GetObject looks for a @emph{class} of a particular type
2.671 +(that again inherits from @code{Object}) and possibly returns an aggregated
2.672 +object instance of that type.
2.673 +
2.674 +Now that you have those conceptual connectors snapped together, you can ask
2.675 +each of the @code{Object}s in the aggregation for any of the @code{Object}s
2.676 +in the aggregation. For example we could walk the @code{Object}s asking each
2.677 +for the next in the aggregation. First we would ask the @code{Object} pointed
2.678 +to by the smart pointer @code{a} to look for the @code{Object} @code{class B}:
2.679
2.680 @verbatim
2.681 - Ptr<B> newB = a->QueryInterface<B> (B:iid);
2.682 + Ptr<B> newB = a->GetObject<B> ();
2.683 @end verbatim
2.684
2.685 -Next, we can ask the Interface pointed to by the smart pointer @code{newB}
2.686 -to look for the @code{InterfaceId} representing @code{C}:
2.687 +Next, we can ask the @code{Object} pointed to by the smart pointer @code{newB}
2.688 +to look for the @code{Object} representing @code{class C}:
2.689
2.690 @verbatim
2.691 - Ptr<C> newC = newB->QueryInterface<C> (C:iid);
2.692 + Ptr<C> newC = newB->GetObject<C> ();
2.693 @end verbatim
2.694
2.695 -Then, we can ask the Interface pointed to by the smart pointer @code{newC}
2.696 -to look for the InterfaceId representing A and complete our circuit of the
2.697 -aggregation:
2.698 +Then, we can ask the @code{Object} pointed to by the smart pointer @code{newC}
2.699 +to look for the @code{Object} representing @code{class A} and complete our
2.700 +circuit of the aggregation:
2.701
2.702 @verbatim
2.703 - Ptr<A> newA = newC->QueryInterface<A> (A:iid);
2.704 + Ptr<A> newA = newC->GetObject<A> ();
2.705 @end verbatim
2.706
2.707 -@code{QueryInterface} (often abbreviated QI) has some important properties
2.708 -that we need to go over. Technically, QI is a @emph{symmetric},
2.709 -@emph{reflexive} and @emph{transitive} operation with respect to the set of
2.710 -aggregated Interfaces.
2.711 +@code{GetObject} has some important properties that we need to go over.
2.712 +Technically, @code{GetObject} is a @emph{symmetric}, @emph{reflexive} and
2.713 +@emph{transitive} operation with respect to the set of aggregated
2.714 +@code{Object}s.
2.715
2.716 @subsubsection Symmetry
2.717 -The symmetric nature of QI guarantees that if one performs a QI on a given
2.718 -Interface for the Interface Id of that same interface, that
2.719 -@code{QueryInterface} must succeed. The existence of interface A in the
2.720 -aggregation implies the reachability of Interface A in the aggregation. This
2.721 -is usually written (by Microsoft) as,
2.722 +The symmetric nature of @code{GetObject} guarantees that if one performs a
2.723 +@code{GetObject} on a given @code{Object} for the class of that same
2.724 +@code{Object}, that @code{GetObject} must succeed. In other words, the
2.725 +fact that you accessed the aggregation via an instance of an @code{Object A}
2.726 +in the aggregation implies the reachability of that @code{Object} in the
2.727 +aggregation. This is usually written (by Microsoft) as,
2.728
2.729 @center must succeed (A >> A)
2.730
2.731 We can illustrate this property with the code snippet,
2.732
2.733 @verbatim
2.734 - Ptr<A> symmetricA = a->QueryInterface<A> (A:iid);
2.735 + Ptr<A> symmetricA = a->GetObject<A> ();
2.736 NS_ASSERT (symmetricA);
2.737 @end verbatim
2.738
2.739 -Here we take as given an interface (smart) pointer named a on which we
2.740 -perform a QI looking for the InterfaceId of that same Interface. This call
2.741 -must always succeed and a smart pointer to the Interface a is returned by QI.
2.742 +Here we take as given an interface (smart) pointer --- named @code{a} --- on
2.743 +which we perform a @code{GetObject} looking for the class that represents that
2.744 +same @code{Object}. This call must always succeed and a smart pointer to the
2.745 +aggregated instance of that class is returned.
2.746
2.747 @subsubsection Reflexivity
2.748 -Calls to QI must also be reflexive. This means that if you successfully QI
2.749 -for interface B from interface A, then you must always be able to QI for A
2.750 -from B. This is usually written as,
2.751 +Calls to @code{GetObject} must also be reflexive. This means that if you
2.752 +successfully @code{GetObject} for @code{Object B} from @code{Object A}, then
2.753 +you must always be able to @code{GetObject} for @code{A} from @code{B}. This
2.754 +is usually written as,
2.755
2.756 @center must succeed (A >> B, then B >> A)
2.757
2.758 This property can be illustrated with the code snippet,
2.759
2.760 @verbatim
2.761 - Ptr<B> b = a->QueryInterface<B> (B:iid);
2.762 - Ptr<A> reflexiveA = b->QueryInterface<A> (A:iid);
2.763 + Ptr<B> b = a->GetObject<B> ();
2.764 + Ptr<A> reflexiveA = b->GetObject<A> ();
2.765 NS_ASSERT (reflexiveA);
2.766 @end verbatim
2.767
2.768 -If the first @code{QueryInterface} on Interface A looking for Interface B
2.769 -succeeds, then a @code{QueryInterface} on Interface B looking for Interface A
2.770 +If the first @code{GetObject} on @code{Object A} looking for @code{Object B}
2.771 +succeeds, then a @code{GetObject} on @code{Object B} looking @code{Object A}
2.772 must succeed.
2.773
2.774 @subsubsection Transitivity
2.775 -@code{QueryInteface} must also be transitive. This means that if one can
2.776 -find Interface B from Interface A, and Interface C from Interface B, then one
2.777 -must also be able to find interface C from Interface A. This is usually
2.778 -written as,
2.779 +@code{GetObject} must also be transitive. This means that if one can
2.780 +find @code{Object B} from @code{Object A}, and @code{Object C} from
2.781 +@code{Object B}, then one must also be able to find @code{Object C} from
2.782 +@code{Object A}. This is usually written as,
2.783
2.784 @center must succeed (A >> B, and B >> C, then A >> C)
2.785
2.786 This property can be illustrated with the code snippet,
2.787
2.788 @verbatim
2.789 - Ptr<B> b = a->QueryInterface<B> (B:iid);
2.790 - Ptr<C> c = b->QueryInterface<C> (C:iid);
2.791 - Ptr<C> transitiveC = a->QueryInterface<C> (C:iid);
2.792 + Ptr<B> b = a->GetObject<B> ();
2.793 + Ptr<C> c = b->GetObject<C> ();
2.794 + Ptr<C> transitiveC = a->GetObject<C> ();
2.795 NS_ASSERT (transitiveC);
2.796 @end verbatim
2.797
2.798 -If you can get to Interface B from Interface A, and you can get to Interface C
2.799 -from Interface B, then a QueryInterface on Interface A looking for Interface C
2.800 -must also succeed.
2.801 +If you can get to @code{Object B} from @code{Object A}, and you can get to
2.802 +@code{Object C} from @code{Object B}, then a @code{GetObject} on
2.803 +@code{Object A} looking for @code{Object C} must also succeed.
2.804
2.805 -@subsection Creating the InterfaceId
2.806 -The final piece of this puzzle is to locate where the interface Ids actually
2.807 -come from. The answer is from a static initializer that must be located in
2.808 -the @code{.cc} file corresponding to the Interface. For example, to
2.809 -initialize the Interface Id for the class A above, you would simply add the
2.810 -following code to the source file that implements class A,
2.811 +@subsection Creating the TypeId
2.812 +The final piece of this puzzle is the @code{TypeId}. Recall that the
2.813 +declaration our eample object above included the following code
2.814
2.815 @verbatim
2.816 - const InterfaceId A::iid =
2.817 - MakeInterfaceId (``A'', Object::iid);
2.818 + static ns3::TypeId GetTypeId (void)
2.819 + {
2.820 + static ns3::TypeId tid = ns3::TypeId ("A")
2.821 + .SetParent (Object::GetTypeId ())
2.822 + .AddConstructor<A> ();
2.823 + return tid;
2.824 + }
2.825 @end verbatim
2.826
2.827 -This code is guaranteed by the C++ language definition to be executed before
2.828 -your main procedure is entered. The call to MakeInterfaceId will assign a
2.829 -process-local unique identifier to your class and associate your interface
2.830 -with the name (string) ``A.'' This allows you to look up an InterfaceId by
2.831 -a human readable string.
2.832 -
2.833 -An advanced ns-3 specific feature of QueryInterface is exposed here.
2.834 -@code{MakeInterfaceId} takes an @code{InterfaceId} as a parameter. This is
2.835 -the @code{iid} of the base class from which you inherited. In most cases
2.836 -this will be @code{Object::iid}, which is the @code{InterfaceId} of the
2.837 -@code{Object} base class. In @command{ns-3}, the @code{Object} base class
2.838 -has its own @code{iid} and you can QI for that @code{iid}. The @code{Object}
2.839 -base class has a rough equivalence to the @emph{IUnknown} Interface in
2.840 -Microsofts COM, so you can QI for @code{Object::iid} in @command{ns-3}f just
2.841 -as you might QI for IID_IUnknown in COM.
2.842 -
2.843 -The InterfaceId you pass to @code{MakeInterfaceId} is used to create an
2.844 -inheritance tree in the ns-3 interface manager. This inheritance tree is also
2.845 -walked in @code{QueryInterface} Interface searches. Consider a simple case
2.846 -of a base class and a derived class as shown below,
2.847 +This is the bit of code that ties this all together. For those unfamiliar
2.848 +with the idioms involved, this declaration can be rather dense. First, let's
2.849 +examine the function declaration itself. The following code,
2.850
2.851 @verbatim
2.852 - class Base : public Object
2.853 + static ns3::TypeId GetTypeId (void) ...
2.854 +@end verbatim
2.855 +
2.856 +declares a function that will be associated with all of the instances of the
2.857 +given class. This is a function, not a method, in that it can be accessed
2.858 +without a @emph{this} pointer; but it is associated with the class in a
2.859 +namespace sense. The use of this kind of declaration allows one to write,
2.860 +
2.861 +@verbatim
2.862 + return A::GetTypeId (void);
2.863 +@end verbatim
2.864 +
2.865 +if the @code{TypeId} is needed for our @code{class A}. More generically the
2.866 +class name can be substituted in a template, as is done deep in the
2.867 +@command{ns-3} object system.
2.868 +
2.869 +From this perspective, if you leave out the middle of the function definition,
2.870 +the boundaries should make sense to you.
2.871 +
2.872 +@verbatim
2.873 + static ns3::TypeId GetTypeId (void)
2.874 + {
2.875 + return tid;
2.876 + }
2.877 +@end verbatim
2.878 +
2.879 +You are obviously looking at a global function associated with your class
2.880 +that simply returns a @code{TypeId}. Now, what about the rest. The code
2.881 +
2.882 +@verbatim
2.883 + static ns3::TypeId tid = ns3::TypeId ("A")
2.884 + .SetParent (Object::GetTypeId ())
2.885 + .AddConstructor<A> ();
2.886 +@end verbatim
2.887 +
2.888 +when found inside the function declaration is called a function-local variable
2.889 +with associated initialization. It'll be easier to pick this statement apart
2.890 +piece by piece as well. The first line,
2.891 +
2.892 +@verbatim
2.893 + static ns3::TypeId tid = ...
2.894 +@end verbatim
2.895 +
2.896 +is the declaration of the function-local variable tid. This is essentially
2.897 +an initialized global variable, the scope of which has been reduced to within
2.898 +the enclosing method. You can think of this as a kind of global variable
2.899 +that can only be accessed right there where it is created. If the variable
2.900 +is initialized, this amounts to the same behavior as if a global static
2.901 +initializer was declared in a namespace of the same name as your class.
2.902 +Global static initializers are guaranteed by the C++ language definition to
2.903 +be executed before your main procedure is entered. So are function-local
2.904 +variables.
2.905 +
2.906 +The variable that is being initialized is of type @code{ns3::TypeId}, is
2.907 +named @code{A::tid} since it is inside the class declaration for
2.908 +@code{class A}, and is initialized by a call to the constructor for the class
2.909 +@code{TypeId}. The constructor for @code{TypeId} takes a @code{std::string}
2.910 +that can be used to locate the type information for your class. We usually
2.911 +privide the class name as the string.
2.912 +
2.913 +Hopefully, this much of the declaration is now clear:
2.914 +
2.915 +@verbatim
2.916 + static ns3::TypeId GetTypeId (void)
2.917 + {
2.918 + static ns3::TypeId tid = ns3::TypeId ("A")
2.919 + ...
2.920 + return tid;
2.921 + }
2.922 +@end verbatim
2.923 +
2.924 +All that is left now are the lines including @code{SetParent} and
2.925 +@code{AddConstructor}.
2.926 +
2.927 +@verbatim
2.928 + static ns3::TypeId tid = ns3::TypeId ("A")
2.929 + .SetParent (Object::GetTypeId ())
2.930 + .AddConstructor<A> ();
2.931 +@end verbatim
2.932 +
2.933 +The last bit may seem quite odd at first glance, but don't let the way the
2.934 +code is broken up over several lines throw you. If you saw something like,
2.935 +
2.936 +@verbatim
2.937 + pointer->TypeId()->SetParent()->AddConstructor();
2.938 +@end verbatim
2.939 +
2.940 +you probably wouldn't hesitate at all. Clearly, you would think, a method
2.941 +called @code{TypeId} is called using the pointer called @code{pointer} as
2.942 +shown below.
2.943 +
2.944 +@verbatim
2.945 + pointer->TypeId()
2.946 +@end verbatim
2.947 +
2.948 +The method @code{TypeId} must further return a pointer to an object that has
2.949 +a method called @code{SetParent}. Just as clearly, @code{SetParent} must
2.950 +return a pointer to an object that has a method called @code{AddConstructor}.
2.951 +The same sort of thing is happening in our code snipped, except we are using
2.952 +references instead of pointers. Perhaps if we rearrange this code to live on
2.953 +one line it will be clearer.
2.954 +
2.955 +@verbatim
2.956 + ns3::TypeId ("A").SetParent (Object::GetTypeId ()).AddConstructor<A> ();
2.957 +@end verbatim
2.958 +
2.959 +It's just a string of method calls. The remaining question is then, what do
2.960 +those three methods do.
2.961 +
2.962 +The first, @code{ns3::TypeId ("A")}, simply allocates a new type in the system
2.963 +and allows you to refer to it in the future by a string. We have mentioned
2.964 +inheritance trees often in the previous discussion. The second method,
2.965 +@code{SetParent} associates the class being defined with its parents in the
2.966 +tree. Finally, the @code{AddConstructor} method allows you to specify a
2.967 +constructor to be used when an instance of your class is created using
2.968 +@code{CreateObject}.
2.969 +
2.970 +@verbatim
2.971 + AddConstructor<A> ();
2.972 +@end verbatim
2.973 +
2.974 +You can interpret this as explaining to the @command{ns-3} object ssytem that
2.975 +you have a constructor named @code{A::A} which takes no parameters. You are
2.976 +saying that this constructor should be used when @code{CreateObject} is called
2.977 +with no parameters.
2.978 +
2.979 +By including the structure of the inheritance tree, in @command{ns-3} we can
2.980 +use implementation inheritance to easily create new @code{Objects}. You are
2.981 +prevented from doing so in Microsoft COM, but this was almost universally
2.982 +identified as a problem.
2.983 +
2.984 +@subsection A Very Real Example
2.985 +At this point you may be asking yourself what the point of all of this is,
2.986 +since you already had those pointers laying around when you created the
2.987 +objects. The typical case is that one will create and aggregate some number
2.988 +of @code{Object}s in a constructor and return only a pointer to a single
2.989 +@code{Object} as in our canonical example with @code{class Node}. In this
2.990 +case, the @code{Node} would be created and the @code{Node} constructor might
2.991 +create and call @code{AggregateObject} to aggregate the @code{Object}s for
2.992 +internetwork routing and TCP/IP. From an external point of view, these
2.993 +aggregated objects may be discovered at run-time using @code{GetObject}.
2.994 +
2.995 +Generally one tends to think of one of the @code{Object}s in the aggregation
2.996 +as being the container and other @code{Objects} being aggregated to that
2.997 +container. In the case of a Node, for example, it is quite natural to think
2.998 +of the Node as being the container which contains protocol stacks, internet
2.999 +routing, etc. So, lets start thinking about a real example by calling the
2.1000 +container @code{Object Node} instead of @code{A} as we have been. The
2.1001 +creation of this @code<Object> is found all over our example programs. For
2.1002 +example, you will find code like the following in
2.1003 +@code{samples/simple-point-to-point.cc}:
2.1004 +
2.1005 +@verbatim
2.1006 + Ptr<Node> n = CreateObject<InternetNode> ();
2.1007 +@end verbatim
2.1008 +
2.1009 +It may appear obvious to you now that the @code{InternetNode} class name
2.1010 +provided to the template function @code{CreateObject} means that
2.1011 +@code{InternetNode} is an @command{ns-3} @code{Object} and you will be able to
2.1012 +call @code{GetObject} on the resulting smart pointer. Well, I'm afraid that's
2.1013 +not entirely true. It's slightly more complicated.
2.1014 +
2.1015 +Take a look at @code{src/internet-node/internet-node.h} and find the class
2.1016 +declaration for @code{InternetNode}.
2.1017 +
2.1018 +@verbatim
2.1019 + class InternetNode : public Node
2.1020 {
2.1021 public:
2.1022 - static const InterfaceId iid;
2.1023 - ...
2.1024 - };
2.1025 -
2.1026 - class Derived : public Base
2.1027 - {
2.1028 - public:
2.1029 - static const InterfaceId iid;
2.1030 + InternetNode();
2.1031 ...
2.1032 };
2.1033 @end verbatim
2.1034
2.1035 -To assign the InterfaceId for each of these classes, we could add two calls
2.1036 -to @code{MakeInterfaceId} reflecting the class hierarchy we just created.
2.1037 +There is no declaration of a @code{static TypeId GetTypeId (void)} in this
2.1038 +class. This means that the @code{InternetNode} is really not an @code{Object}
2.1039 +for which you can @code{GetObject}. It turns out that the @code{InternetNode}
2.1040 +is an @emph{implementation class} of the @code{Node Object}.
2.1041
2.1042 -@verbatim
2.1043 - const InterfaceId Base::iid =
2.1044 - MakeInterfaceId (``Base'', Object::iid);
2.1045 -
2.1046 - const InterfaceId Derived::iid =
2.1047 - MakeInterfaceId (``Derived'', Base::iid);
2.1048 -@end verbatim
2.1049 -
2.1050 -The first Interface is shown to inherit from class @code{Object} and the
2.1051 -second inherits from class @code{Base}. We could create these interfaces
2.1052 -as we usually do,
2.1053 -
2.1054 -@verbatim
2.1055 -Ptr<Base> base = Create<Base> ();
2.1056 -Ptr<Derived> derived = Create<Derived> ();
2.1057 -@end verbatim
2.1058 -
2.1059 -The derived and base @code{InterfaceIds} are either present or not present
2.1060 -based on the inheritance tree. For example, a QI for the @code{Base
2.1061 -InterfaceId} must succeed when done against a @code{Ptr<Base>}; but a QI for
2.1062 -the @code{Derived InterfaceId} must fail when done against a @code{Ptr<Base>}.
2.1063 -However, a QI for the @code{Base InterfaceId} must succeed when done against a
2.1064 -@code{Ptr<Derived>}; and a QI for the @code{Derived InterfaceId} must succeed
2.1065 -when done against a @code{Ptr<Derived>}.
2.1066 -
2.1067 -This feature allows you to use implementation inheritance to easily create
2.1068 -new Interfaces. You are prevented from doing so in Microsoft COM, but this
2.1069 -was almost universally identified as a problem.
2.1070 -
2.1071 -@subsection A Real Example
2.1072 -At this point you may be asking yourself what the point of all of this is,
2.1073 -since you already had those pointers laying around when you created the
2.1074 -objects. The typical case is that you would forget about the pointers to the
2.1075 -contained objects and only export a single Interface. Other Interfaces could
2.1076 -be discovered using QI.
2.1077 -
2.1078 -Generally one tends to think of one of the Interfaces in the aggregation
2.1079 -as being the container and other Interfaces being aggregated to that
2.1080 -container. In the case of a Node, for example, it is quite natural to think
2.1081 -of the Node as being the container which contains Interfaces for the protocol
2.1082 -stacks, internet routing, etc. So, lets start developing an example by
2.1083 -calling the container Interface Node instead of A. The creation of this
2.1084 -Interface is found all over our example programs. For example, you will
2.1085 -find code like the following in @code{samples/simple-point-to-point.cc}:
2.1086 -
2.1087 -@verbatim
2.1088 - Ptr<Node> n = Create<InternetNode> ();
2.1089 -@end verbatim
2.1090 -
2.1091 -This code is described in detail in previous sections, but the important thing
2.1092 -to realize here is that the resulting @code{Node} is an @command{ns-3}
2.1093 -Interface. This is not at all obvious -- you must look at the source code to
2.1094 -see that this is true. Take a look at @code{src/node/node.h} and find the
2.1095 -class declaration for class @code{Node}. There you will find,
2.1096 +You may recall that there can be an implicit cast in a smart pointer
2.1097 +assignment if the cast is to a visible, unambiguous base class. That is, in
2.1098 +fact, what is happening here. Now, take a look at @code{src/node/node.h} and
2.1099 +find the class declaration for @code{class Node}. There you will find,
2.1100
2.1101 @verbatim
2.1102 class Node : public Object
2.1103 {
2.1104 public:
2.1105 - static const InterfaceId iid;
2.1106 + static TypeId GetTypeId (void);
2.1107 ...
2.1108 };
2.1109 @end verbatim
2.1110
2.1111 -Class @code{Node} inherits from class @code{Object} and provides an
2.1112 -@code{InterfaceId}, therefore it is an @command{ns-3} interface. You now
2.1113 -know you can use @code{AddInterface} for aggregation and @code{QueryInterface}
2.1114 -for Interface discovery against any @code{Node} in the system.
2.1115 +Class @code{InternetNode} inherits from class @code{Node} that, in turn,
2.1116 +inherits from class @code{Object}. It is @code{Node} that provides a
2.1117 +@code{GetTypeId} method. Therefore it is @code{Node} that is an
2.1118 +@command{ns-3} @code{Object}. Note well that @code{InternetNode} is not an
2.1119 +@code{Object} in the sense that one should call @code{GetObject} on an
2.1120 +aggregation looking for an @code{InternetNode} class. That is, you should not
2.1121 +do,
2.1122 +
2.1123 +@verbatim
2.1124 + Ptr<InternetNode> i = node->GetObject<InternetNode> ();
2.1125 +@end verbatim
2.1126 +
2.1127 +since there really is not InternetNode::GetTypeId. It is @code{Node} that is
2.1128 +the @emph{proper} @code{Object} in this case and you should view
2.1129 +@code{InternetNode} as an implementation of the @code{Node Object}. This may
2.1130 +become clearer as we look a little deeper.
2.1131
2.1132 We spoke of a protocol stack that is aggregated to a @code{Node} in our
2.1133 discussions above, what we see in the real @command{ns-3} code is that this
2.1134 -is represented by the @code{Ipv4} Interface. If you look in
2.1135 +is represented by the @code{Ipv4 Object}. If you look in
2.1136 @code{src/node/ipv4.h} you will find,
2.1137
2.1138 @verbatim
2.1139 class Ipv4 : public Object
2.1140 {
2.1141 public:
2.1142 - static const InterfaceId iid;
2.1143 + static TypeId GetTypeId (void);
2.1144 ...
2.1145 };
2.1146 @end verbatim
2.1147
2.1148 Since class @code{Ipv4} inherits from class @code{Object} and has a
2.1149 -@code{static InterfaceId}, it is an @command{ns-3} Interface. If you look in
2.1150 +@code{GetTypeId}, it is an @command{ns-3} @code{Object}. If you look in
2.1151 @code{src/node/ipv4.cc} you will find,
2.1152
2.1153 @verbatim
2.1154 - const InterfaceId Ipv4::iid =
2.1155 - MakeInterfaceId (``Ipv4'', Object::iid);
2.1156 +TypeId
2.1157 +Ipv4::GetTypeId (void)
2.1158 +{
2.1159 + static TypeId tid = TypeId ("Ipv4")
2.1160 + .SetParent<Object> ();
2.1161 + return tid;
2.1162 +}
2.1163 @end verbatim
2.1164
2.1165 -After all of this reading you now know that this code snippet is asking the
2.1166 -system to create a unique @code{InterfaceId} for the @code{Ipv4} class and
2.1167 -declares that @code{Ipv4} inherits from class @code{Object}.
2.1168 +After all of this reading you know that this code snippet is asking the
2.1169 +system to create a unique @code{TypeId} for the @code{Ipv4} class and
2.1170 +declares that @code{Ipv4} inherits from class @code{Object}. This is what
2.1171 +makes an @code{Ipv4} an @code{Object}.
2.1172
2.1173 It turns out that the Ipv4 class is an abstract base class (ABC). There are
2.1174 a number of pure virtual methods declared in that class. This means that
2.1175 -an @code{Ipv4} object may not be instantiated. What is instantiated is an
2.1176 -implementation class, called @code{Ipv4Impl}. This class inherits from
2.1177 -@code{Ipv4} and provides the required virtual methods. This is where
2.1178 -understanding what is an Interface and what is not gets tricky. The
2.1179 -Interface is the @code{Ipv4} class since that is where the @code{InterfaceId}
2.1180 -is found. The fact that you see @code{ipv4::iid} tells you that the
2.1181 -@code{Ipv4} class is the Interface and has the associated @code{InterfaceId}.
2.1182 +an @code{Ipv4} object may not be instantiated. This is reflected by the fact
2.1183 +that there are no constructors registered in the @code{GetTypeId} method above.
2.1184 +What is instantiated in the real system is an implementation class, called
2.1185 +@code{Ipv4Impl}. This class inherits from @code{Ipv4} and provides the
2.1186 +required virtual methods. This is where understanding what is an
2.1187 +@code{Object} and what is not can get tricky. The @code{Object} is the
2.1188 +@code{Ipv4} class since that is where the @code{GetTypeId} is found. The fact
2.1189 +that you see @code{GetTypeId} there tells you that the @code{Ipv4} class is
2.1190 +the class for which you can @code{GetObject}.
2.1191 +
2.1192 The class @code{Ipv4Impl} provides an implementation for the pure virtual
2.1193 methods in @code{Ipv4}. Since class @code{Ipv4} cannot be instantiated, one
2.1194 -instantiates the @code{Ipv4Impl} class to create an @code{Ipv4} Interface.
2.1195 -Once the @code{Ipv4Impl} class is instantiated, the pointer to it is
2.1196 +instantiates the @code{Ipv4Impl} class to create an @code{Ipv4} @code{Object}.
2.1197 +You will use the @code{CreateObject} template function to create an object that
2.1198 +implements the methods of an @code{Object}. You can probably see how this
2.1199 +gets even more tricky in conversation.
2.1200 +
2.1201 +Once the @code{Ipv4Impl} object is instantiated, the resulting pointer is
2.1202 immediately cast to an @code{Ipv4} pointer. Clients will then use the
2.1203 -@code{Ipv4} object access methods (see @code{ipv4.h}) to talk to the
2.1204 -@code{Ipv4Impl} object over the @code{Ipv4} Interface. I urge you to not go
2.1205 -any further until you thoroughly understand what youve just read.
2.1206 +methods specified in the @code{Ipv4} class to access the @code{Ipv4 Object}
2.1207 +methods which are, in turn, implemented in the @code{Ipv4Impl} object.
2.1208
2.1209 If you now look in the file, @code{src/internet-node/internet-node.cc} you
2.1210 will see the following code in @code{InternetNode::Construct} that creates the
2.1211 -@code{Ipv4} Interface and aggregates it to the @code{Node} interface (recall
2.1212 -that class @code{Node} is an Interface and class @code{InternetNode} inherits
2.1213 -from class @code{Node}):
2.1214 +@code{Ipv4} Interface and aggregates it.
2.1215
2.1216 @verbatim
2.1217 - Ptr<Ipv4Impl> ipv4Impl = Create<Ipv4Impl> (ipv4);
2.1218 + Ptr<Ipv4Impl> ipv4Impl = CreateObject<Ipv4Impl> (ipv4);
2.1219 ...
2.1220 - Object::AddInterface (ipv4Impl);
2.1221 + Object::AggregateObject (ipv4Impl);
2.1222 @end verbatim
2.1223
2.1224 -Note that the parameter @code{ipv4} passed to the @code{Create} template
2.1225 +Note that the parameter @code{ipv4} passed to the @code{CreateObject} template
2.1226 function is actually a pointer to an @code{Ipv4L3Protocol} which you can
2.1227 ignore at this point --- it doesn't really have anything to do with the
2.1228 @code{Ipv4} Interface.
2.1229
2.1230 -This last example does illustrate that the fact that whether an @command{ns-3}
2.1231 -object is or is not an Interface can be quite well hidden. The designers of
2.1232 -the system had long and involved discussions on this issue and in the end
2.1233 -decided that mnemonic aids such as Hungarian notation were a stylistic thing
2.1234 -and you should just refer to the system documentation to determine what
2.1235 -objects are ns-3 Interfaces and what those Interfaces actually are (RTFM ---
2.1236 -Read the Fine Manual).
2.1237 -
2.1238 -In this case, you know that the class @code{Ipv4Impl} inherits from some
2.1239 -Interface since there is a call to @code{AddInterface} that refers to it.
2.1240 -You can go to the header file @code{src/internet-node/ipv4-impl.h} and find
2.1241 -that @code{Ipv4Impl} inherits from class @code{Ipv4}. You then go to file
2.1242 -@code{src/node/ipv4.h} and see that it inherits from @code{Object} and
2.1243 -contains an @code{InterfaceId}. Thus the Interface added is really the
2.1244 -@code{Ipv4} Interface with the interface Id @code{Ipv4::iid}.
2.1245 -
2.1246 -Returning to some @command{ns-3} example code, lets take a look at
2.1247 -@code{src/examples/simple-point-to-point.cc} again. You will find the
2.1248 -following code:
2.1249 +This is exactly the same thing that is happening in the case of the
2.1250 +@code{InternetNode}.
2.1251
2.1252 @verbatim
2.1253 - Ptr<Node> n0 = Create<InternetNode> ();
2.1254 + Ptr<Node> n = CreateObject<InternetNode> ();
2.1255 +@end verbatim
2.1256 +
2.1257 +@code{CreateObject} is being called to create an implementation object,
2.1258 +in this case @code{InternetNode}, which implements the methods of the
2.1259 +@code{Node Object}. It is the resulting @code{Node Object} which you would
2.1260 +use as the container and it is the @code{Node} class that you would use as
2.1261 +the template parameter when calling @code{GetObject}. In the same way, you
2.1262 +would @emph{not} want to do,
2.1263 +
2.1264 +@verbatim
2.1265 + Ptr<Ipv4> ipv4 = node->GetObject<Ipv4Impl> ();
2.1266 +@end verbatim
2.1267 +
2.1268 +Rather you should understand that the @emph{proper} @code{Object} is the
2.1269 +@code{Ipv4} not the @code{Ipv4Impl} and do the following,
2.1270 +
2.1271 +@verbatim
2.1272 + Ptr<Ipv4> ipv4 = node->GetObject<Ipv4> ();
2.1273 +@end verbatim
2.1274 +
2.1275 +This does illustrate that the fact that whether an object created by
2.1276 +@code{CreateObject} is or is not an @code{Object} in the usual sense can be
2.1277 +quite well hidden if you are casually looking at the object creation code.
2.1278 +The designers of the system had long and involved discussions on this issue
2.1279 +and in the end decided that mnemonic aids such as Hungarian notation were a
2.1280 +stylistic thing and you should just refer to the system documentation to
2.1281 +determine what objects are @command{ns-3} @code{Object}s and what the APIs
2.1282 +of those @code{Object}s actually are (RTFM --- as in Read the Fine Manual,
2.1283 +of course).
2.1284 +
2.1285 +In the case of @code{Ipv4Impl}, you know that the class inherits somehow
2.1286 +from @code{Object} since there is a call to @code{AggregateObject} that
2.1287 +refers to an instance of an @code{Ipv4Impl}. You will have to go to
2.1288 +the header file @code{src/internet-node/ipv4-impl.h} and find that
2.1289 +@code{Ipv4Impl} inherits from class @code{Ipv4}. You will then have go to
2.1290 +the file @code{src/node/ipv4.h} and see that it inherits from @code{Object} and
2.1291 +defines a @code{GetTypeId}. Thus the @code{Object} for which you can
2.1292 +@code{GetObject} is really the @code{Ipv4 Object}.
2.1293 +
2.1294 +Returning to some real @command{ns-3} example code, lets take a look at
2.1295 +@code{examples/simple-point-to-point.cc}. You will find the following
2.1296 +code in this file:
2.1297 +
2.1298 +@verbatim
2.1299 + Ptr<Node> n0 = CreateObject<InternetNode> ();
2.1300 ...
2.1301 Ptr<Ipv4> ipv4;
2.1302 - ipv4 = n0->QueryInterface<Ipv4> (Ipv4::iid);
2.1303 + ipv4 = n0->GetObject<Ipv4> ();
2.1304 ipv4->SetDefaultRoute (Ipv4Address (``10.1.1.2''), 1);
2.1305 @end verbatim
2.1306
2.1307 -The first line creates an @code{InternetNode} object and casts the resulting
2.1308 -smart pointer to a @code{Node}. The next line declares a smart pointer to an
2.1309 -@code{Ipv4} object. Because youve been through the code with us, you know
2.1310 -that both the @code{Node} and the @code{Ipv4} objects are Interfaces. They
2.1311 -should be able to participate in a @code{QueryInterface}.
2.1312 -
2.1313 -The next line confirms it. We do a @code{QueryInterface} on the @code{Node},
2.1314 -looking for the @code{Ipv4} Interface (@code{Ipv4::iid}).
2.1315 -@code{QueryInterface} then returns a smart pointer to its aggregated
2.1316 -@code{Ipv4} Interface. [Recall that this Interface was aggregated in
2.1317 -@code{InternetNode::Construct}. We knew to start looking for the aggregation
2.1318 -in @code{InternetNode} since we originally created an @code{InternetNode} in
2.1319 -the @code{Create} template function and then implicitly cast it to a
2.1320 -@code{Node}.]
2.1321 -
2.1322 -Once you have the @code{Ipv4} smart pointer, you simply use it as if it were
2.1323 -any other C++ object. The last line shows this by setting the default route
2.1324 -for the node.
2.1325 +The first line creates an @code{InternetNode} implementation object and casts
2.1326 +the resulting smart pointer to a @code{Node} as we have discussed extensively.
2.1327 +The next line shown declares a smart pointer to an @code{Ipv4 Object}. We
2.1328 +then do a @code{GetObject} on the @code{Node} looking for the
2.1329 +@code{Ipv4 Object}. You know since you've read every line of this tutorial
2.1330 +in detail exactly how that @code{Ipv4 Object} got into every @code{Node}. You
2.1331 +know that the @code{GetObject} will return a smart pointer to its aggregated
2.1332 +@code{Ipv4} Interface. Once we have the @code{Ipv4} smart pointer, we simply
2.1333 +use it as if it were any other C++ object. The last line shows this by
2.1334 +setting the default route for the node.
2.1335
2.1336 @section Caveats
2.1337 There are a few things that you should remember but which may not be
2.1338 immediately obvious.
2.1339
2.1340 -@subsection Interface Ids are Associated with Classes not Objects
2.1341 -Interfaces are identified by an @code{InterfaceId} that is associated with
2.1342 -the Interface class, not the Interface object. That is indicated by the
2.1343 -@code{static} keyword in the declaration of the @code{iid} in the class. The
2.1344 -interface Id for a given Interface class exists independently of any objects
2.1345 -of that class that you may instantiate; and all objects of a given Interface
2.1346 -type share the same @code{InterfaceId}.
2.1347 +@subsection Ns-3 Objects are Associated with Classes not C++ objects
2.1348 +Okay, you can see some of the problems with the terminology popping up again.
2.1349 +We are reminding you that when you do a GetObject you are providing the key
2.1350 +to the lookup by giving a class name and not anything that is unique to a
2.1351 +C++ object.
2.1352
2.1353 -You cannot add more than one Interface of a given type (@code{iid}) to an
2.1354 -aggregation. If you need to contain a number of Interfaces of the same type
2.1355 -in the same aggregation, you will need to provide a separate container over
2.1356 -which you can iterate. For example, the @code{Node} class provides methods,
2.1357 +You cannot add more than one @code{Object} of a given type (class name) to an
2.1358 +aggregation. If you need to contain a number of @code{Object}s of the same
2.1359 +type in the same aggregation, you will need to provide a separate container
2.1360 +over which you can iterate. For example, the @code{Node} class provides
2.1361 +methods,
2.1362
2.1363 @verbatim
2.1364 uint32_t GetNDevices (void) const;
2.1365 Ptr<NetDevice> GetDevice (uint32_t index) const;
2.1366 @end verbatim
2.1367
2.1368 -that are used iterate over the multiple @code{NetDevice} Interfaces associated
2.1369 -with it.
2.1370 +that are used iterate over the multiple @code{NetDevice} @code{Object}s
2.1371 +associated with it.
2.1372
2.1373 -@emph{Interface Ids do not identify objects.}
2.1374 +@emph{Remember: Object types do not identify objects.}
2.1375
2.1376 @subsection Dont use QI to Check Your Own Type.
2.1377 -It is tempting to use @code{QueryInterface} as a form of runtime type
2.1378 -information. Dont do it. You have no control over what other object may be
2.1379 -added to your aggregation and this may cause problems. Someone else may have
2.1380 -appropriated (reimplemented) your type and aggregated themselves onto your
2.1381 +It is tempting to use @code{GetObject} as a form of runtime type
2.1382 +information. Dont do it. You have no control over what @emph{other}
2.1383 +object may be added to your aggregation. Someone else may have
2.1384 +appropriated (reimplemented) your type and aggregated themselves onto the
2.1385 aggregation.
2.1386
2.1387 Consider a socket factory implementation. Sockets can be either UDP sockets
2.1388 or TCP sockets. A socket factory will have a generic @code{SocketFactory}
2.1389 -Interface and either a UDP specific interface for setting UDP parameters or a
2.1390 +Object and either a UDP specific interface for setting UDP parameters or a
2.1391 similar TCP-specific interface.
2.1392
2.1393 Consider what might happen if you declared your socket factory as a partially
2.1394 abstract base class, and then provided separate implementations for UDP and
2.1395 TCP specific methods of this factory in separate concrete classes. Now
2.1396 -consider what might happen if you used QueryInterface in your base class
2.1397 +consider what might happen if you used @code{GetObject} in your base class
2.1398 to determine if you were a UDP or a TCP factory.
2.1399
2.1400 -If a factory, say the UDP version, were not aggregated to any other Interface,
2.1401 -the base class could QueryInterface on itself for the UDP-specific interface.
2.1402 -It could then infer that it was a UDP implementation and would then do any
2.1403 -UDP-specific tasks it could. [Experienced C++ folks are cringing about how
2.1404 +If a factory, say the UDP version, were not aggregated to any other
2.1405 +@code{Object}, the base class could @code{GetObject} on itself for the
2.1406 +UDP-specific class name. If the @code{GetObject} succeeded, it could then
2.1407 +infer that it was a UDP implementation and would then do any UDP-specific
2.1408 +tasks it could. [Experienced C++ folks are cringing about how
2.1409 horrible this design is, but bear with me --- its a simple illustration of
2.1410 a specific and perhaps not-too-obvious problem.]
2.1411
2.1412 If another factory, say the TCP version, were not aggregated to any other
2.1413 -Interface, the base class could QueryInterface on itself for the UDP-specific
2.1414 +Interface, the base class could @code{GetObject} on itself for the UDP-specific
2.1415 interface. If this failed, it could then infer that it had a TCP
2.1416 implementation and would then do any TCP-specific tasks it could.
2.1417
2.1418 -Now, what happens when these two working objects are aggregated together.
2.1419 -Since the Interfaces are conceptually snapped together the TCP implementation
2.1420 -would suddenly begin finding the UDP Interface from the other class factory
2.1421 -and fail.
2.1422 +Now, what happens when these two working objects are aggregated together by
2.1423 +some innocent end-user. Since the @code{Object}s are conceptually snapped
2.1424 +together, the TCP implementation would suddenly begin finding the UDP
2.1425 +Interface from the other class factory and think it was the UPD implementation.
2.1426
2.1427 -@emph{Interface Ids should not be used as run-time type information.}
2.1428 +@emph{Objects should not be used as run-time type information.}
2.1429
2.1430 @section Connecting the Dots
2.1431 This may all sound very complicated to you if this is your first exposure to
2.1432 these concepts. It may be annoying if I tell you that its really not as hard
2.1433 as it sounds. Rest assured that if you take some time, look at and understand
2.1434 the examples and write a little test code it will all come together for you.
2.1435 -Grep around the system for AddInterface and QueryInterface and take a look at
2.1436 -how we have used them. This will also give you a good idea of what our core
2.1437 -Interfaces are. If you grep for @code{::iid} you will find most, if not all
2.1438 -of the interface declarations in the system. The more you see this idiom in
2.1439 +Grep around the system for @code{AggregateObject} and @code{GetObject} and
2.1440 +take a look at how we have used them. This will also give you a good idea of
2.1441 +what our core @code{Object}s and associated APIs are. If you grep for
2.1442 +@code{GetTypeId} you will find most, if not all of the @code{Object} API
2.1443 +interface declarations in the system. The more you see this idiom in
2.1444 use, the more comfortable you will be with the idea and the more you will see
2.1445 how this addresses the weak base class, swiss army knife base class, and
2.1446 fragile base class problems I explained at the beginning.
2.1447
2.1448 As I alluded to earlier, the developers had long discussions regarding how to
2.1449 -make navigating the QueryInterface environment easier. The primary issue was
2.1450 +make navigating the @code{Object} environment easier. The primary issue was
2.1451 how we could make it easier to convey to you, the model writer, that an object
2.1452 -was an Interface. One suggestion was to adopt the convention that classes
2.1453 -that implement Interfaces begin with the letter I. Microsoft does this, as
2.1454 -exemplified by the class IUnknown. We also toyed with the idea of beginning
2.1455 -our header files with i- as in i-ipv4.h. We considered forcing some structure
2.1456 -on Interfaces with a pure virtual class specification, the names of which
2.1457 -begin with an I; and corresponding implementations, the names of which begin
2.1458 -with a C.
2.1459 +was an @code{Object}. We originally used similar terminology as Microsoft
2.1460 +COM and used QueryInterface instead of @code{GetObject}. One suggestion was
2.1461 +to adopt the convention that classes that implemented Interfaces must begin
2.1462 +with the letter I. Microsoft does this, as exemplified by the class IUnknown.
2.1463 +We also toyed with the idea of beginning our header files with ``i-'' as in
2.1464 +``i-ipv4.h.'' We considered forcing some structure on Interfaces with a pure
2.1465 +virtual class specification, the names of which begin with an I; and
2.1466 +corresponding implementations, the names of which begin with a C. This all
2.1467 +got out of hand fairly quickly.
2.1468
2.1469 In the end we decided that we were really discussing issues of programming
2.1470 style, and we really could not come up with a strong reason to impose any
2.1471 -particular solution. In the end, we decided that we would not impose any
2.1472 -structure on the source code, nor impose any naming convention. We will
2.1473 -rely on our documentation system (Doxygen) to break out all objects with
2.1474 -InterfaceIds in their class hierarchy into a separate section. For now,
2.1475 -until this is implemented, grep is your friend.
2.1476 +particular solution. No matter what direction we took, we ended up with some
2.1477 +form of extra confusion or extra complexity somewhere in the system. The
2.1478 +resulting system is extremely flexible and easy to use. It is, unfortunately,
2.1479 +sometimes hard to document and talk about.
2.1480 +
2.1481 +If it helps you to think in terms of Microsoft COM and Interfaces, by all means
2.1482 +do so, just be aware that even though @command{ns-3} @code{Object}s descend
2.1483 +from COM in some sense, there are subtle differences that may get you lost or
2.1484 +into trouble. So to paraphrase Feynman one more time,
2.1485 +
2.1486 +@quotation
2.1487 +``@command{Ns-3} @code{Objects} do not behave like COM Components, or Java
2.1488 +Beans, or CORBA objects, or clouds or weights on springs, or like anything
2.1489 +that you have ever seen --- they are @command{ns-3} components.''
2.1490 +@end quotation
2.1491 +
2.1492 +Just get very familiar with the @command{ns-3} object model. It is the heart
2.1493 +of the system and if you do not understand it you will not understand how to
2.1494 +write an @command{ns-3} model properly.
2.1495
2.1496 @c ========================================================================
2.1497 @c Doxygen
3.1 --- a/doc/tutorial/output.texi Tue Feb 05 15:29:17 2008 -0500
3.2 +++ b/doc/tutorial/output.texi Tue Feb 05 15:30:16 2008 -0500
3.3 @@ -108,7 +108,7 @@
3.4
3.5 Try running the following program from the command line:
3.6 @verbatim
3.7 - ./waf --run csma-echo-ascii-trace
3.8 + ./waf --run tutorial-csma-echo-ascii-trace
3.9 @end verbatim
3.10
3.11 @cindex tutorial.tr
3.12 @@ -391,12 +391,12 @@
3.13 many tools available for analyzing pcap traces; below, we show how
3.14 tcpdump and Wireshark can be used..
3.15
3.16 -@cindex csma-echo-ascii-trace.cc
3.17 -@cindex csma-echo-pcap-trace.cc
3.18 +@cindex tutorial-csma-echo-ascii-trace.cc
3.19 +@cindex tutorial-csma-echo-pcap-trace.cc
3.20 The code used to enable pcap tracing is similar to that for ASCII tracing.
3.21 -We have provided another file, @code{csma-echo-pcap-trace.cc} that uses the
3.22 -pcap trace wrapper. We have added the code to include the pcap trace wrapper
3.23 -defintions:
3.24 +We have provided another file, @code{tutorial-csma-echo-pcap-trace.cc} that
3.25 +uses the pcap trace wrapper. We have added the code to include the pcap
3.26 +trace wrapper defintions:
3.27
3.28 @verbatim
3.29 #include "ns3/pcap-trace.h"
3.30 @@ -432,7 +432,7 @@
3.31
3.32 @cindex Waf
3.33 @verbatim
3.34 - ./waf --run csma-echo-pcap-trace
3.35 + ./waf --run tutorial-csma-echo-pcap-trace
3.36 @end verbatim
3.37
3.38 If you look at the top level directory of your distribution, you should now
4.1 --- a/doc/tutorial/routing.texi Tue Feb 05 15:29:17 2008 -0500
4.2 +++ b/doc/tutorial/routing.texi Tue Feb 05 15:30:16 2008 -0500
4.3 @@ -6,7 +6,7 @@
4.4 module, and some details about the routing approachs currently
4.5 implemented.
4.6
4.7 -@node Overview
4.8 +@node Routing-Overview
4.9 @section Overview
4.10
4.11 We intend to support traditional routing approaches and protocols,
4.12 @@ -341,8 +341,8 @@
4.13 for (Iterator i = NodeList::Begin (); i != NodeList::End (); i++)
4.14 {
4.15 Ptr<Node> node = *i;
4.16 - Ptr<GlobalRouter> globalRouter = Create<GlobalRouter> (node);
4.17 - node->AddInterface (globalRouter);
4.18 + Ptr<GlobalRouter> globalRouter = CreateObject<GlobalRouter> (node);
4.19 + node->AggregateObject (globalRouter);
4.20 }
4.21 @end verbatim
4.22
5.1 --- a/doc/tutorial/troubleshoot.texi Tue Feb 05 15:29:17 2008 -0500
5.2 +++ b/doc/tutorial/troubleshoot.texi Tue Feb 05 15:30:16 2008 -0500
5.3 @@ -66,12 +66,12 @@
5.4
5.5 Let's look around line 136 of tcp-point-to-point, as gdb suggests:
5.6 @verbatim
5.7 - Ptr<SocketFactory> socketFactory = n2->QueryInterface<SocketFactory> (Tcp::iid);
5.8 + Ptr<SocketFactory> socketFactory = n2->GetObject<SocketFactory> (Tcp::iid);
5.9 Ptr<Socket> localSocket = socketFactory->CreateSocket ();
5.10 localSocket->Bind ();
5.11 @end verbatim
5.12
5.13 -The culprit here is that the return value of QueryInterface is not being
5.14 +The culprit here is that the return value of GetObject is not being
5.15 checked and may be null.
5.16
5.17 Sometimes you may need to use the @uref{http://valgrind.org,,valgrind memory
6.1 --- a/doc/tutorial/tutorial.texi Tue Feb 05 15:29:17 2008 -0500
6.2 +++ b/doc/tutorial/tutorial.texi Tue Feb 05 15:30:16 2008 -0500
6.3 @@ -66,7 +66,7 @@
6.4 @contents
6.5
6.6 @ifnottex
6.7 -@node Top, Introduction, Full Table of Contents
6.8 +@node Top, Overview, Full Table of Contents
6.9 @top ns-3 Tutorial (html version)
6.10
6.11 For a pdf version of this tutorial,
6.12 @@ -76,14 +76,15 @@
6.13 @end ifnottex
6.14
6.15 @menu
6.16 -* Introduction::
6.17 -Part 1: Overview
6.18 +* Tutorial Goals::
6.19 +Part 1: Getting Started with ns-3
6.20 * Overview::
6.21 +* Browsing::
6.22 * Resources::
6.23 -* The-Basics::
6.24 +* Downloading and Compiling::
6.25 * Some-Prerequisites::
6.26 * A-First-ns-3-Script::
6.27 -Part 2: Details
6.28 +Part 2-: Details
6.29 * ns-3 Callbacks::
6.30 * Simulation Output::
6.31 * ns-3 routing overview::
7.1 --- a/examples/simple-point-to-point-olsr.cc Tue Feb 05 15:29:17 2008 -0500
7.2 +++ b/examples/simple-point-to-point-olsr.cc Tue Feb 05 15:30:16 2008 -0500
7.3 @@ -21,7 +21,7 @@
7.4 //
7.5 // Network topology
7.6 //
7.7 -// n0
7.8 +// n0
7.9 // \ 5 Mb/s, 2ms
7.10 // \ 1.5Mb/s, 10ms
7.11 // n2 -------------------------n3
7.12 @@ -151,13 +151,12 @@
7.13 channel2, n2, Ipv4Address("10.1.3.1"),
7.14 n3, Ipv4Address("10.1.3.2"));
7.15
7.16 - // Finally, we add static routes. These three steps (Channel and
7.17 - // NetDevice creation, IP Address assignment, and routing) are
7.18 - // separated because there may be a need to postpone IP Address
7.19 - // assignment (emulation) or modify to use dynamic routing
7.20 +
7.21 + // Enable OLSR
7.22 NS_LOG_INFO ("Enabling OLSR Routing.");
7.23 olsr::EnableAllNodes ();
7.24
7.25 +
7.26 // Create the OnOff application to send UDP datagrams of size
7.27 // 210 bytes at a rate of 448 Kb/s
7.28 NS_LOG_INFO ("Create Applications.");
7.29 @@ -170,7 +169,6 @@
7.30 ConstantVariable(0));
7.31 // Start the application
7.32 ooff->Start(Seconds(1.0));
7.33 - ooff->Stop (Seconds(10.0));
7.34
7.35 // Create an optional packet sink to receive these packets
7.36 Ptr<PacketSink> sink = CreateObject<PacketSink> (
7.37 @@ -179,7 +177,6 @@
7.38 "Udp");
7.39 // Start the sink
7.40 sink->Start (Seconds (1.0));
7.41 - sink->Stop (Seconds (10.0));
7.42
7.43 // Create a similar flow from n3 to n1, starting at time 1.1 seconds
7.44 ooff = CreateObject<OnOffApplication> (
7.45 @@ -189,8 +186,7 @@
7.46 ConstantVariable(1),
7.47 ConstantVariable(0));
7.48 // Start the application
7.49 - ooff->Start(Seconds(1.1));
7.50 - ooff->Stop (Seconds(10.0));
7.51 + ooff->Start (Seconds(1.1));
7.52
7.53 // Create a packet sink to receive these packets
7.54 sink = CreateObject<PacketSink> (
7.55 @@ -199,17 +195,7 @@
7.56 "Udp");
7.57 // Start the sink
7.58 sink->Start (Seconds (1.1));
7.59 - sink->Stop (Seconds (10.0));
7.60
7.61 - // Here, finish off packet routing configuration
7.62 - // This will likely set by some global StaticRouting object in the future
7.63 - NS_LOG_INFO ("Set Default Routes.");
7.64 - Ptr<Ipv4> ipv4;
7.65 - ipv4 = n0->GetObject<Ipv4> ();
7.66 - ipv4->SetDefaultRoute (Ipv4Address ("10.1.1.2"), 1);
7.67 - ipv4 = n3->GetObject<Ipv4> ();
7.68 - ipv4->SetDefaultRoute (Ipv4Address ("10.1.3.1"), 1);
7.69 -
7.70 // Configure tracing of all enqueue, dequeue, and NetDevice receive events
7.71 // Trace output will be sent to the simple-point-to-point.tr file
7.72 NS_LOG_INFO ("Configure Tracing.");
7.73 @@ -226,8 +212,8 @@
7.74 pcaptrace.TraceAllIp ();
7.75
7.76 NS_LOG_INFO ("Run Simulation.");
7.77 - Simulator::StopAt (Seconds (10));
7.78 - Simulator::Run ();
7.79 + Simulator::StopAt (Seconds (30));
7.80 + Simulator::Run ();
7.81 Simulator::Destroy ();
7.82 NS_LOG_INFO ("Done.");
7.83 }
8.1 --- a/examples/simple-point-to-point.cc Tue Feb 05 15:29:17 2008 -0500
8.2 +++ b/examples/simple-point-to-point.cc Tue Feb 05 15:30:16 2008 -0500
8.3 @@ -72,29 +72,7 @@
8.4 // Users may find it convenient to turn on explicit debugging
8.5 // for selected modules; the below lines suggest how to do this
8.6 #if 0
8.7 - LogComponentEnable ("SimplePointToPointExample", LOG_LEVEL_INFO);
8.8 -
8.9 - LogComponentEnable("Object", LOG_LEVEL_ALL);
8.10 - LogComponentEnable("Queue", LOG_LEVEL_ALL);
8.11 - LogComponentEnable("DropTailQueue", LOG_LEVEL_ALL);
8.12 - LogComponentEnable("Channel", LOG_LEVEL_ALL);
8.13 - LogComponentEnable("CsmaChannel", LOG_LEVEL_ALL);
8.14 - LogComponentEnable("NetDevice", LOG_LEVEL_ALL);
8.15 - LogComponentEnable("CsmaNetDevice", LOG_LEVEL_ALL);
8.16 - LogComponentEnable("Ipv4L3Protocol", LOG_LEVEL_ALL);
8.17 - LogComponentEnable("PacketSocket", LOG_LEVEL_ALL);
8.18 - LogComponentEnable("Socket", LOG_LEVEL_ALL);
8.19 - LogComponentEnable("UdpSocket", LOG_LEVEL_ALL);
8.20 - LogComponentEnable("UdpL4Protocol", LOG_LEVEL_ALL);
8.21 - LogComponentEnable("Ipv4L3Protocol", LOG_LEVEL_ALL);
8.22 - LogComponentEnable("Ipv4StaticRouting", LOG_LEVEL_ALL);
8.23 - LogComponentEnable("Ipv4Interface", LOG_LEVEL_ALL);
8.24 - LogComponentEnable("ArpIpv4Interface", LOG_LEVEL_ALL);
8.25 - LogComponentEnable("Ipv4LoopbackInterface", LOG_LEVEL_ALL);
8.26 - LogComponentEnable("OnOffApplication", LOG_LEVEL_ALL);
8.27 - LogComponentEnable("PacketSinkApplication", LOG_LEVEL_ALL);
8.28 - LogComponentEnable("UdpEchoClientApplication", LOG_LEVEL_ALL);
8.29 - LogComponentEnable("UdpEchoServerApplication", LOG_LEVEL_ALL);
8.30 + LogComponentEnable ("SimplePointToPointExample", LOG_LEVEL_ALL);
8.31 #endif
8.32
8.33 // Set up some default values for the simulation. Use the Bind()
8.34 @@ -108,8 +86,6 @@
8.35 DefaultValue::Bind ("OnOffApplicationPacketSize", "210");
8.36 DefaultValue::Bind ("OnOffApplicationDataRate", "448kb/s");
8.37
8.38 - //DefaultValue::Bind ("DropTailQueue::m_maxPackets", 30);
8.39 -
8.40 // Allow the user to override any of the defaults and the above
8.41 // Bind()s at run-time, via command-line arguments
8.42 CommandLine::Parse (argc, argv);
8.43 @@ -170,8 +146,7 @@
8.44 ConstantVariable(1),
8.45 ConstantVariable(0));
8.46 // Start the application
8.47 - ooff->Start(Seconds(1.0));
8.48 - ooff->Stop (Seconds(10.0));
8.49 + ooff->Start (Seconds(1.0));
8.50
8.51 // Create an optional packet sink to receive these packets
8.52 Ptr<PacketSink> sink = CreateObject<PacketSink> (
8.53 @@ -180,7 +155,6 @@
8.54 "Udp");
8.55 // Start the sink
8.56 sink->Start (Seconds (1.0));
8.57 - sink->Stop (Seconds (10.0));
8.58
8.59 // Create a similar flow from n3 to n1, starting at time 1.1 seconds
8.60 ooff = CreateObject<OnOffApplication> (
8.61 @@ -191,7 +165,6 @@
8.62 ConstantVariable(0));
8.63 // Start the application
8.64 ooff->Start(Seconds(1.1));
8.65 - ooff->Stop (Seconds(10.0));
8.66
8.67 // Create a packet sink to receive these packets
8.68 sink = CreateObject<PacketSink> (
8.69 @@ -200,7 +173,27 @@
8.70 "Udp");
8.71 // Start the sink
8.72 sink->Start (Seconds (1.1));
8.73 - sink->Stop (Seconds (10.0));
8.74 +
8.75 + // TCP
8.76 + // Create a file transfer from n0 to n3, starting at time 1.2
8.77 + uint16_t servPort = 500;
8.78 +
8.79 + ooff = CreateObject<OnOffApplication> (
8.80 + n0,
8.81 + InetSocketAddress ("10.1.3.2", servPort),
8.82 + "Tcp",
8.83 + ConstantVariable(1),
8.84 + ConstantVariable(0));
8.85 + // Start the application
8.86 + ooff->Start (Seconds(1.2));
8.87 + ooff->Stop (Seconds(1.35));
8.88 +
8.89 + // Create a packet sink to receive these TCP packets
8.90 + sink = Create<PacketSink> (
8.91 + n3,
8.92 + InetSocketAddress (Ipv4Address::GetAny (), servPort),
8.93 + "Tcp");
8.94 + sink->Start (Seconds (1.2));
8.95
8.96 // Here, finish off packet routing configuration
8.97 // This will likely set by some global StaticRouting object in the future
8.98 @@ -227,7 +220,7 @@
8.99 pcaptrace.TraceAllIp ();
8.100
8.101 NS_LOG_INFO ("Run Simulation.");
8.102 - Simulator::StopAt (Seconds (10));
8.103 + Simulator::StopAt (Seconds (3.0));
8.104 Simulator::Run ();
8.105 Simulator::Destroy ();
8.106 NS_LOG_INFO ("Done.");
9.1 --- a/src/applications/onoff/onoff-application.cc Tue Feb 05 15:29:17 2008 -0500
9.2 +++ b/src/applications/onoff/onoff-application.cc Tue Feb 05 15:30:16 2008 -0500
9.3 @@ -195,6 +195,7 @@
9.4 NS_LOG_FUNCTION;
9.5
9.6 Simulator::Cancel(m_sendEvent);
9.7 + m_socket->Close ();
9.8 }
9.9
9.10 // Private helpers
10.1 --- a/src/internet-node/tcp-socket.cc Tue Feb 05 15:29:17 2008 -0500
10.2 +++ b/src/internet-node/tcp-socket.cc Tue Feb 05 15:30:16 2008 -0500
10.3 @@ -121,6 +121,7 @@
10.4 m_node = 0;
10.5 m_endPoint = 0;
10.6 m_tcp = 0;
10.7 + m_retxEvent.Cancel ();
10.8 }
10.9 int
10.10 TcpSocket::FinishBind (void)
11.1 --- a/src/internet-node/udp-socket.cc Tue Feb 05 15:29:17 2008 -0500
11.2 +++ b/src/internet-node/udp-socket.cc Tue Feb 05 15:30:16 2008 -0500
11.3 @@ -276,15 +276,19 @@
11.4 //
11.5 if (dest.IsBroadcast ())
11.6 {
11.7 - NS_LOG_LOGIC ("Limited broadcast");
11.8 + NS_LOG_LOGIC ("Limited broadcast start.");
11.9 for (uint32_t i = 0; i < ipv4->GetNInterfaces (); i++ )
11.10 {
11.11 Ipv4Address addri = ipv4->GetAddress (i);
11.12 Ipv4Mask maski = ipv4->GetNetworkMask (i);
11.13 - m_udp->Send (p->Copy (), addri, addri.GetSubnetDirectedBroadcast (maski),
11.14 + Ipv4Address bcast = addri.GetSubnetDirectedBroadcast (maski);
11.15 + NS_LOG_LOGIC ("Sending one copy from " << addri << " to " << bcast
11.16 + << " (mask is " << maski << ")");
11.17 + m_udp->Send (p->Copy (), addri, bcast,
11.18 m_endPoint->GetLocalPort (), port);
11.19 NotifyDataSent (p->GetSize ());
11.20 }
11.21 + NS_LOG_LOGIC ("Limited broadcast end.");
11.22 }
11.23 else if (ipv4->GetIfIndexForDestination(dest, localIfIndex))
11.24 {
12.1 --- a/src/node/socket.h Tue Feb 05 15:29:17 2008 -0500
12.2 +++ b/src/node/socket.h Tue Feb 05 15:30:16 2008 -0500
12.3 @@ -78,21 +78,24 @@
12.4 * \param closeCompleted Callback invoked when the close operation is
12.5 * completed.
12.6 */
12.7 - void SetCloseCallback (Callback<void,Ptr<Socket> > closeCompleted);
12.8 + void SetCloseCallback (Callback<void, Ptr<Socket> > closeCompleted);
12.9
12.10 /**
12.11 - * \param connectionSucceeded this callback is invoked when the connection request
12.12 - * initiated by the user is successfully completed. The callback is passed
12.13 - * back a pointer to the same socket object.
12.14 - * \param connectionFailed this callback is invoked when the connection request
12.15 - * initiated by the user is unsuccessfully completed. The callback is passed
12.16 - * back a pointer to the same socket object.
12.17 - * \param halfClose XXX When exactly is this callback invoked ? If it invoked when the
12.18 - * other side closes the connection ? Or when I call Close ?
12.19 + * \param connectionSucceeded this callback is invoked when the
12.20 + * connection request initiated by the user is successfully
12.21 + * completed. The callback is passed back a pointer to
12.22 + * the same socket object.
12.23 + * \param connectionFailed this callback is invoked when the
12.24 + * connection request initiated by the user is unsuccessfully
12.25 + * completed. The callback is passed back a pointer to the
12.26 + * same socket object.
12.27 + * \param halfClose XXX When exactly is this callback invoked? If
12.28 + * it invoked when the other side closes the connection ?
12.29 + * Or when I call Close ?
12.30 */
12.31 void SetConnectCallback (Callback<void, Ptr<Socket> > connectionSucceeded,
12.32 - Callback<void, Ptr<Socket> > connectionFailed,
12.33 - Callback<void, Ptr<Socket> > halfClose);
12.34 + Callback<void, Ptr<Socket> > connectionFailed,
12.35 + Callback<void, Ptr<Socket> > halfClose);
12.36 /**
12.37 * \brief Accept connection requests from remote hosts
12.38 * \param connectionRequest Callback for connection request from peer.
12.39 @@ -100,28 +103,31 @@
12.40 * ip address and the port number of the connection originator.
12.41 * This callback must return true to accept the incoming connection,
12.42 * false otherwise. If the connection is accepted, the
12.43 - * "newConnectionCreated" callback will be invoked later to give access
12.44 - * to the user to the socket created to match this new connection. If the
12.45 - * user does not explicitely specify this callback, all incoming
12.46 - * connections will be refused.
12.47 + * "newConnectionCreated" callback will be invoked later to
12.48 + * give access to the user to the socket created to match
12.49 + * this new connection. If the user does not explicitly
12.50 + * specify this callback, all incoming connections will be refused.
12.51 * \param newConnectionCreated Callback for new connection: when a new
12.52 * is accepted, it is created and the corresponding socket is passed
12.53 - * back to the user through this callback. This user callback is passed
12.54 - * a pointer to the new socket, and the ip address and port number
12.55 - * of the connection originator.
12.56 + * back to the user through this callback. This user callback is
12.57 + * passed a pointer to the new socket, and the ip address and
12.58 + * port number of the connection originator.
12.59 * \param closeRequested Callback for connection close request from peer.
12.60 * XXX: when is this callback invoked ?
12.61 */
12.62 - void SetAcceptCallback (Callback<bool, Ptr<Socket>, const Address &> connectionRequest,
12.63 - Callback<void, Ptr<Socket>, const Address&> newConnectionCreated,
12.64 - Callback<void, Ptr<Socket> > closeRequested);
12.65 + void SetAcceptCallback (Callback<bool, Ptr<Socket>,
12.66 + const Address &> connectionRequest,
12.67 + Callback<void, Ptr<Socket>,
12.68 + const Address&> newConnectionCreated,
12.69 + Callback<void, Ptr<Socket> > closeRequested);
12.70 void SetSendCallback (Callback<void, Ptr<Socket>, uint32_t> dataSent);
12.71 /**
12.72 * \brief Receive data
12.73 * \param receivedData Invoked whenever new data is received.
12.74 *
12.75 */
12.76 - void SetRecvCallback (Callback<void, Ptr<Socket>, Ptr<Packet>,const Address&> receivedData);
12.77 + void SetRecvCallback (Callback<void, Ptr<Socket>, Ptr<Packet>,
12.78 + const Address&> receivedData);
12.79
12.80 /**
12.81 * \param address the address to try to allocate
13.1 --- a/src/routing/olsr/olsr-agent-impl.cc Tue Feb 05 15:29:17 2008 -0500
13.2 +++ b/src/routing/olsr/olsr-agent-impl.cc Tue Feb 05 15:30:16 2008 -0500
13.3 @@ -167,6 +167,7 @@
13.4 m_tcTimer (Timer::CANCEL_ON_DESTROY),
13.5 m_midTimer (Timer::CANCEL_ON_DESTROY)
13.6 {
13.7 + NS_LOG_DEBUG ("Created olsr::AgentImpl");
13.8 m_helloTimer.SetFunction (&AgentImpl::HelloTimerExpire, this);
13.9 m_tcTimer.SetFunction (&AgentImpl::TcTimerExpire, this);
13.10 m_midTimer.SetFunction (&AgentImpl::MidTimerExpire, this);
13.11 @@ -345,6 +346,18 @@
13.12 DuplicateTuple *duplicated = m_state.FindDuplicateTuple
13.13 (messageHeader.GetOriginatorAddress (),
13.14 messageHeader.GetMessageSequenceNumber ());
13.15 +
13.16 + // Get main address of the peer, which may be different from the packet source address
13.17 + const IfaceAssocTuple *ifaceAssoc = m_state.FindIfaceAssocTuple (inetSourceAddr.GetIpv4 ());
13.18 + Ipv4Address peerMainAddress;
13.19 + if (ifaceAssoc != NULL)
13.20 + {
13.21 + peerMainAddress = ifaceAssoc->mainAddr;
13.22 + }
13.23 + else
13.24 + {
13.25 + peerMainAddress = inetSourceAddr.GetIpv4 () ;
13.26 + }
13.27
13.28 if (duplicated == NULL)
13.29 {
13.30 @@ -352,17 +365,17 @@
13.31 {
13.32 case olsr::MessageHeader::HELLO_MESSAGE:
13.33 NS_LOG_DEBUG ("OLSR node received HELLO message of size " << messageHeader.GetSerializedSize ());
13.34 - ProcessHello (messageHeader, m_mainAddress, inetSourceAddr.GetIpv4 ());
13.35 + ProcessHello (messageHeader, m_mainAddress, peerMainAddress);
13.36 break;
13.37
13.38 case olsr::MessageHeader::TC_MESSAGE:
13.39 NS_LOG_DEBUG ("OLSR node received TC message of size " << messageHeader.GetSerializedSize ());
13.40 - ProcessTc (messageHeader, inetSourceAddr.GetIpv4 ());
13.41 + ProcessTc (messageHeader, peerMainAddress);
13.42 break;
13.43
13.44 case olsr::MessageHeader::MID_MESSAGE:
13.45 NS_LOG_DEBUG ("OLSR node received MID message of size " << messageHeader.GetSerializedSize ());
13.46 - ProcessMid (messageHeader, inetSourceAddr.GetIpv4 ());
13.47 + ProcessMid (messageHeader, peerMainAddress);
13.48 break;
13.49
13.50 default:
13.51 @@ -395,7 +408,7 @@
13.52 // Remaining messages are also forwarded using the default algorithm.
13.53 if (messageHeader.GetMessageType () != olsr::MessageHeader::HELLO_MESSAGE)
13.54 ForwardDefault (messageHeader, duplicated,
13.55 - m_mainAddress, inetSourceAddr.GetIpv4 ());
13.56 + m_mainAddress, peerMainAddress);
13.57 }
13.58
13.59 }
13.60 @@ -775,13 +788,13 @@
13.61 {
13.62 RoutingTableEntry entry;
13.63 bool foundEntry = m_routingTable->Lookup (nb2hop_tuple.neighborMainAddr, entry);
13.64 - if (!foundEntry)
13.65 - NS_FATAL_ERROR ("m_routingTable->Lookup failure");
13.66 -
13.67 - m_routingTable->AddEntry (nb2hop_tuple.twoHopNeighborAddr,
13.68 - entry.nextAddr,
13.69 - entry.interface,
13.70 - 2);
13.71 + if (foundEntry)
13.72 + {
13.73 + m_routingTable->AddEntry (nb2hop_tuple.twoHopNeighborAddr,
13.74 + entry.nextAddr,
13.75 + entry.interface,
13.76 + 2);
13.77 + }
13.78 }
13.79 }
13.80
13.81 @@ -1239,7 +1252,7 @@
13.82 }
13.83 if (!ok)
13.84 {
13.85 - NS_ASSERT (!"Link tuple has no corresponding neighbor tuple\n");
13.86 + continue;
13.87 }
13.88 }
13.89
14.1 --- a/src/routing/olsr/routing-table.cc Tue Feb 05 15:29:17 2008 -0500
14.2 +++ b/src/routing/olsr/routing-table.cc Tue Feb 05 15:30:16 2008 -0500
14.3 @@ -40,6 +40,7 @@
14.4 void
14.5 RoutingTable::Clear ()
14.6 {
14.7 + NS_LOG_FUNCTION;
14.8 m_table.clear ();
14.9 }
14.10
14.11 @@ -119,7 +120,7 @@
14.12 Ipv4Route route = Ipv4Route::CreateHostRouteTo
14.13 (ipHeader.GetDestination (), entry2.nextAddr, entry2.interface);
14.14
14.15 - NS_LOG_DEBUG ("Olsr node" << m_mainAddress
14.16 + NS_LOG_DEBUG ("Olsr node " << m_mainAddress
14.17 << ": RouteRequest for dest=" << ipHeader.GetDestination ()
14.18 << " --> destHop=" << entry2.nextAddr
14.19 << " interface=" << entry2.interface);
14.20 @@ -129,9 +130,19 @@
14.21 }
14.22 else
14.23 {
14.24 - NS_LOG_DEBUG ("Olsr node" << m_mainAddress
14.25 + NS_LOG_DEBUG ("Olsr node " << m_mainAddress
14.26 << ": RouteRequest for dest=" << ipHeader.GetDestination ()
14.27 - << " --> NOT FOUND");
14.28 + << " --> NOT FOUND; ** Dumping routing table...");
14.29 +#if 0
14.30 + for (std::map<Ipv4Address, RoutingTableEntry>::const_iterator iter = m_table.begin ();
14.31 + iter != m_table.end (); iter++)
14.32 + {
14.33 + NS_LOG_DEBUG ("dest=" << iter->first << " --> next=" << iter->second.nextAddr
14.34 + << " via interface " << iter->second.interface);
14.35 + }
14.36 +
14.37 + NS_LOG_DEBUG ("** Routing table dump end.");
14.38 +#endif
14.39 return false;
14.40 }
14.41 }
14.42 @@ -172,6 +183,14 @@
14.43 uint32_t interface,
14.44 uint32_t distance)
14.45 {
14.46 + NS_LOG_PARAMS_BEGIN ();
14.47 + NS_LOG_PARAM (this);
14.48 + NS_LOG_PARAM (dest);
14.49 + NS_LOG_PARAM (next);
14.50 + NS_LOG_PARAM (interface);
14.51 + NS_LOG_PARAM (distance);
14.52 + NS_LOG_PARAM (m_mainAddress);
14.53 + NS_LOG_PARAMS_END ();
14.54 // Creates a new rt entry with specified values
14.55 RoutingTableEntry &entry = m_table[dest];
14.56
14.57 @@ -187,6 +206,14 @@
14.58 Ipv4Address const &interfaceAddress,
14.59 uint32_t distance)
14.60 {
14.61 + NS_LOG_PARAMS_BEGIN ();
14.62 + NS_LOG_PARAM (this);
14.63 + NS_LOG_PARAM (dest);
14.64 + NS_LOG_PARAM (next);
14.65 + NS_LOG_PARAM (interfaceAddress);
14.66 + NS_LOG_PARAM (distance);
14.67 + NS_LOG_PARAM (m_mainAddress);
14.68 + NS_LOG_PARAMS_END ();
14.69 RoutingTableEntry entry;
14.70 NS_ASSERT (m_ipv4);
14.71 for (uint32_t i = 0; i < m_ipv4->GetNInterfaces (); i++)
15.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
15.2 +++ b/tutorial/energy-model.cc Tue Feb 05 15:30:16 2008 -0500
15.3 @@ -0,0 +1,132 @@
15.4 +/* -*- Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
15.5 +/*
15.6 + * Copyright (c) 2007 University of Washington
15.7 + *
15.8 + * This program is free software; you can redistribute it and/or modify
15.9 + * it under the terms of the GNU General Public License version 2 as
15.10 + * published by the Free Software Foundation;
15.11 + *
15.12 + * This program is distributed in the hope that it will be useful,
15.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
15.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15.15 + * GNU General Public License for more details.
15.16 + *
15.17 + * You should have received a copy of the GNU General Public License
15.18 + * along with this program; if not, write to the Free Software
15.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
15.20 + */
15.21 +
15.22 +#include "ns3/log.h"
15.23 +#include "energy-model.h"
15.24 +
15.25 +NS_LOG_COMPONENT_DEFINE("EnergyModel");
15.26 +
15.27 +namespace ns3 {
15.28 +
15.29 +//
15.30 +// Some dimensional analysis ...
15.31 +//
15.32 +// 1 [watt] = 1 [joule] / [second]
15.33 +// 1 [watt] = 1 [volt] * 1 [amp]
15.34 +// 1 [amp] = 1 [coulomb] / 1 [second]
15.35 +// 1 [watt-second] = 1 [joule] / [second] * [second] = 1 [joule]
15.36 +//
15.37 +// A watt has dimensions of energy per second. A watt-second has dimensions
15.38 +// of energy.
15.39 +//
15.40 +// 1 [amp-hour] = 1 [coulomb] / 1 [second] * 1 [hour]
15.41 +// 1 [amp-hour] = 1 [coulomb] / 1 [second] * 3600 [seconds]
15.42 +// 1 [amp-hour] = 3600 [amp-seconds]
15.43 +// 1 [watt-second] = 1 [amp-seconds] * 1 [volt]
15.44 +//
15.45 +// To get the energy capacity of your battery in watt-seconds from its
15.46 +// amp-hour rating, multiply by 3600 and then the voltage. For example, your
15.47 +// Alkaline AAA battery may be rated at 1.5 volts and 900 milli-amp-hours;
15.48 +// so the energy capacity will be .9 * 3600 * 1.5 = 4860 watt-seconds.
15.49 +//
15.50 +// In a very simple battery model, we'll take this naively to mean that this
15.51 +// battery can supply one watt continuously for 4860 seconds and then will die
15.52 +// instantaneously.
15.53 +//
15.54 +// We'll assume our transmitter is measured in watts. When it is turned on
15.55 +// it draws some amount of power, 100 milliwatts for example. If it transmits
15.56 +// for one second, it will suck up .1 watt-seconds of our precious energy.
15.57 +//
15.58 +
15.59 +const InterfaceId EnergyModel::iid =
15.60 + MakeInterfaceId ("EnergyModel", Object::iid);
15.61 +
15.62 +
15.63 +EnergyModel::EnergyModel (
15.64 + double ampHours,
15.65 + double volts,
15.66 + double idlePower,
15.67 + double receivePower,
15.68 + double transmitPower)
15.69 +:
15.70 + m_capacity (ampHours * 3600. * volts),
15.71 + m_idlePower (idlePower),
15.72 + m_receivePower (receivePower),
15.73 + m_transmitPower (transmitPower),
15.74 + m_totalTransmitPower (0.),
15.75 + m_totalReceivePower (0.)
15.76 +{
15.77 + NS_LOG_FUNCTION;
15.78 + SetInterfaceId (EnergyModel::iid);
15.79 +}
15.80 +
15.81 +EnergyModel::~EnergyModel ()
15.82 +{
15.83 + NS_LOG_FUNCTION;
15.84 +}
15.85 +
15.86 + double
15.87 +EnergyModel::GetCapacity (Time t)
15.88 +{
15.89 + NS_LOG_FUNCTION;
15.90 + double c = m_capacity - m_idlePower * t.GetSeconds ();
15.91 + return c >= 0. ? c : 0.;
15.92 +}
15.93 +
15.94 + double
15.95 +EnergyModel::GetTotalIdlePower (Time t)
15.96 +{
15.97 + NS_LOG_FUNCTION;
15.98 + return m_idlePower * t.GetSeconds ();
15.99 +}
15.100 +
15.101 + double
15.102 +EnergyModel::GetTotalReceivePower (void)
15.103 +{
15.104 + NS_LOG_FUNCTION;
15.105 + return m_totalReceivePower;
15.106 +}
15.107 +
15.108 + double
15.109 +EnergyModel::GetTotalTransmitPower (void)
15.110 +{
15.111 + NS_LOG_FUNCTION;
15.112 + return m_totalTransmitPower;
15.113 +}
15.114 +
15.115 + bool
15.116 +EnergyModel::DrawTransmitPower (Time t)
15.117 +{
15.118 + NS_LOG_FUNCTION;
15.119 + double power = m_transmitPower * t.GetSeconds ();
15.120 + m_totalTransmitPower += power;
15.121 + m_capacity -= power;
15.122 + return m_capacity - m_idlePower * t.GetSeconds () >= 0. ? true : false;
15.123 +}
15.124 +
15.125 + bool
15.126 +EnergyModel::DrawReceivePower (Time t)
15.127 +{
15.128 + NS_LOG_FUNCTION;
15.129 + double power = m_receivePower * t.GetSeconds ();
15.130 + m_totalReceivePower += power;
15.131 + m_capacity -= power;
15.132 + return m_capacity - m_idlePower * t.GetSeconds () >= 0. ? true : false;
15.133 +}
15.134 +
15.135 +}; // namespace ns3
16.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
16.2 +++ b/tutorial/energy-model.h Tue Feb 05 15:30:16 2008 -0500
16.3 @@ -0,0 +1,62 @@
16.4 +/* -*- Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
16.5 +/*
16.6 + * Copyright (c) 2007 University of Washington
16.7 + *
16.8 + * This program is free software; you can redistribute it and/or modify
16.9 + * it under the terms of the GNU General Public License version 2 as
16.10 + * published by the Free Software Foundation;
16.11 + *
16.12 + * This program is distributed in the hope that it will be useful,
16.13 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
16.14 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16.15 + * GNU General Public License for more details.
16.16 + *
16.17 + * You should have received a copy of the GNU General Public License
16.18 + * along with this program; if not, write to the Free Software
16.19 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
16.20 + */
16.21 +
16.22 +#ifndef ENERGY_MODEL_H
16.23 +#define ENERGY_MODEL_H
16.24 +
16.25 +#include "ns3/object.h"
16.26 +#include "ns3/ptr.h"
16.27 +#include "ns3/nstime.h"
16.28 +
16.29 +namespace ns3 {
16.30 +
16.31 +class EnergyModel : public Object
16.32 +{
16.33 +public:
16.34 + static const InterfaceId iid;
16.35 +
16.36 + EnergyModel (
16.37 + double ampHours,
16.38 + double volts,
16.39 + double idlePower,
16.40 + double receivePower,
16.41 + double transmitPower);
16.42 +
16.43 + virtual ~EnergyModel ();
16.44 +
16.45 + double GetCapacity (Time t);
16.46 +
16.47 + double GetTotalIdlePower (Time t);
16.48 + double GetTotalTransmitPower (void);
16.49 + double GetTotalReceivePower (void);
16.50 +
16.51 + bool DrawTransmitPower (Time t);
16.52 + bool DrawReceivePower (Time t);
16.53 +
16.54 +private:
16.55 + double m_capacity;
16.56 + double m_idlePower;
16.57 + double m_receivePower;
16.58 + double m_transmitPower;
16.59 + double m_totalTransmitPower;
16.60 + double m_totalReceivePower;
16.61 +};
16.62 +
16.63 +}; // namespace ns3
16.64 +
16.65 +#endif /* ENERGY_MODEL_H */
17.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
17.2 +++ b/tutorial/energy.cc Tue Feb 05 15:30:16 2008 -0500
17.3 @@ -0,0 +1,124 @@
17.4 +/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
17.5 +/*
17.6 + * This program is free software; you can redistribute it and/or modify
17.7 + * it under the terms of the GNU General Public License version 2 as
17.8 + * published by the Free Software Foundation;
17.9 + *
17.10 + * This program is distributed in the hope that it will be useful,
17.11 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
17.12 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17.13 + * GNU General Public License for more details.
17.14 + *
17.15 + * You should have received a copy of the GNU General Public License
17.16 + * along with this program; if not, write to the Free Software
17.17 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17.18 + */
17.19 +
17.20 +#include "ns3/log.h"
17.21 +#include "ns3/ptr.h"
17.22 +#include "ns3/internet-node.h"
17.23 +#include "ns3/point-to-point-channel.h"
17.24 +#include "ns3/mac48-address.h"
17.25 +#include "ns3/point-to-point-net-device.h"
17.26 +#include "ns3/point-to-point-topology.h"
17.27 +#include "ns3/udp-echo-client.h"
17.28 +#include "ns3/udp-echo-server.h"
17.29 +#include "ns3/simulator.h"
17.30 +#include "ns3/nstime.h"
17.31 +#include "ns3/ascii-trace.h"
17.32 +#include "ns3/pcap-trace.h"
17.33 +#include "ns3/global-route-manager.h"
17.34 +
17.35 +#include "energy-model.h"
17.36 +
17.37 +NS_LOG_COMPONENT_DEFINE ("EnergyModelInterfaceExample");
17.38 +
17.39 +using namespace ns3;
17.40 +
17.41 +// Network topology
17.42 +//
17.43 +// point to point
17.44 +// +--------------+
17.45 +// | |
17.46 +// n0 n1
17.47 +//
17.48 +int
17.49 +main (int argc, char *argv[])
17.50 +{
17.51 + LogComponentEnable ("EnergyModelInterfaceExample", LOG_LEVEL_ALL);
17.52 + // LogComponentEnable ("EnergyModel", LOG_LEVEL_ALL);
17.53 +
17.54 + NS_LOG_INFO ("Energy Model Interface Example");
17.55 +
17.56 + NS_LOG_INFO ("Creating Nodes");
17.57 + Ptr<Node> n0 = CreateObject<InternetNode> ();
17.58 + Ptr<Node> n1 = CreateObject<InternetNode> ();
17.59 +
17.60 + NS_LOG_INFO ("Creating Channel");
17.61 + Ptr<PointToPointChannel> link = PointToPointTopology::AddPointToPointLink (
17.62 + n0, n1, DataRate (38400), MilliSeconds (20));
17.63 +
17.64 + PointToPointTopology::AddIpv4Addresses (link, n0, "10.1.1.1",
17.65 + n1, "10.1.1.2");
17.66 +
17.67 + NS_LOG_INFO ("Creating Applications");
17.68 + uint16_t port = 7;
17.69 +
17.70 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
17.71 + port, 1, Seconds(1.), 1024);
17.72 +
17.73 + Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
17.74 +
17.75 + server->Start(Seconds(1.));
17.76 + client->Start(Seconds(2.));
17.77 +
17.78 + server->Stop (Seconds(10.));
17.79 + client->Stop (Seconds(10.));
17.80 +
17.81 + NS_LOG_INFO ("Initializing Tracing");
17.82 + AsciiTrace asciitrace ("energy.tr");
17.83 + asciitrace.TraceAllQueues ();
17.84 + asciitrace.TraceAllNetDeviceRx ();
17.85 +//
17.86 +// Pick a battery out of the air and use some somewhat real numbers found on
17.87 +// data sheets on the web.
17.88 +//
17.89 +// 2 AAA battery (900 mAh * 2, with imaginary wireless device that uses
17.90 +// 0.350 W at idle power, 0.025 W additional during receive, and 0.2 W
17.91 +// additional power during transmission (10 mW TX power).
17.92 +//
17.93 + NS_LOG_INFO ("Initializing Energy Models");
17.94 + Ptr<EnergyModel> e0 = CreateObject<EnergyModel> (1.8, 1.5, 0.35, 0.025, 0.2);
17.95 + n0->AddInterface (e0);
17.96 +
17.97 + Ptr<EnergyModel> e1 = CreateObject<EnergyModel> (1.8, 1.5, 0.35, 0.025, 0.2);
17.98 + n1->AddInterface (e1);
17.99 +
17.100 +#if 0
17.101 +//
17.102 +// As simulation progresses, the battereis draw idle power. Down in the
17.103 +// net device, we will want to call DrawTransmitPower and DrawReceivePower
17.104 +// as required.
17.105 +//
17.106 +// This is just some example code showing how to draw power and check
17.107 +// consumption.
17.108 +//
17.109 + NS_LOG_INFO("Node zero energy: " << e0->GetCapacity (Seconds (0.)) <<
17.110 + " watt-seconds");
17.111 + NS_LOG_INFO("Node one energy: " << e1->GetCapacity (Seconds (0.)) <<
17.112 + " watt-seconds");
17.113 +
17.114 + e0->DrawTransmitPower (Seconds (0.1));
17.115 + e1->DrawReceivePower (Seconds (0.1));
17.116 + e1->DrawTransmitPower (Seconds (0.1));
17.117 + e0->DrawReceivePower (Seconds (0.1));
17.118 +
17.119 + NS_LOG_INFO("Node zero energy: " << e0->GetCapacity (Seconds (10.)) <<
17.120 + " watt-seconds");
17.121 + NS_LOG_INFO("Node one energy: " << e1->GetCapacity (Seconds (10.)) <<
17.122 + " watt-seconds");
17.123 +#endif
17.124 +
17.125 + Simulator::Run ();
17.126 + Simulator::Destroy ();
17.127 +}
18.1 --- a/tutorial/tutorial-bus-network.cc Tue Feb 05 15:29:17 2008 -0500
18.2 +++ b/tutorial/tutorial-bus-network.cc Tue Feb 05 15:30:16 2008 -0500
18.3 @@ -41,8 +41,8 @@
18.4 uint32_t port = 7;
18.5
18.6 Ptr<Node> n0 = bus.GetNode (0);
18.7 - Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.0.1", port,
18.8 - 1, Seconds(1.), 1024);
18.9 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.0.1",
18.10 + port, 1, Seconds(1.), 1024);
18.11
18.12 Ptr<Node> n1 = bus.GetNode (1);
18.13 Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
19.1 --- a/tutorial/tutorial-csma-echo-ascii-trace.cc Tue Feb 05 15:29:17 2008 -0500
19.2 +++ b/tutorial/tutorial-csma-echo-ascii-trace.cc Tue Feb 05 15:30:16 2008 -0500
19.3 @@ -66,8 +66,8 @@
19.4
19.5 uint16_t port = 7;
19.6
19.7 - Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2", port,
19.8 - 1, Seconds(1.), 1024);
19.9 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
19.10 + port, 1, Seconds(1.), 1024);
19.11
19.12 Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
19.13
20.1 --- a/tutorial/tutorial-csma-echo-pcap-trace.cc Tue Feb 05 15:29:17 2008 -0500
20.2 +++ b/tutorial/tutorial-csma-echo-pcap-trace.cc Tue Feb 05 15:30:16 2008 -0500
20.3 @@ -67,8 +67,8 @@
20.4
20.5 uint16_t port = 7;
20.6
20.7 - Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2", port,
20.8 - 1, Seconds(1.), 1024);
20.9 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
20.10 + port, 1, Seconds(1.), 1024);
20.11
20.12 Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
20.13
21.1 --- a/tutorial/tutorial-csma-echo.cc Tue Feb 05 15:29:17 2008 -0500
21.2 +++ b/tutorial/tutorial-csma-echo.cc Tue Feb 05 15:30:16 2008 -0500
21.3 @@ -65,8 +65,8 @@
21.4
21.5 uint16_t port = 7;
21.6
21.7 - Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2", port,
21.8 - 1, Seconds(1.), 1024);
21.9 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
21.10 + port, 1, Seconds(1.), 1024);
21.11
21.12 Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
21.13
22.1 --- a/tutorial/tutorial-linear-dumbbell.cc Tue Feb 05 15:29:17 2008 -0500
22.2 +++ b/tutorial/tutorial-linear-dumbbell.cc Tue Feb 05 15:30:16 2008 -0500
22.3 @@ -124,14 +124,14 @@
22.4 //
22.5 uint16_t port = 7;
22.6
22.7 - Ptr<UdpEchoClient> client0 = CreateObject<UdpEchoClient> (n0, "10.1.2.1", port,
22.8 - 100, Seconds(.01), 1024);
22.9 - Ptr<UdpEchoClient> client1 = CreateObject<UdpEchoClient> (n1, "10.1.2.2", port,
22.10 - 100, Seconds(.01), 1024);
22.11 - Ptr<UdpEchoClient> client2 = CreateObject<UdpEchoClient> (n2, "10.1.2.3", port,
22.12 - 100, Seconds(.01), 1024);
22.13 - Ptr<UdpEchoClient> client3 = CreateObject<UdpEchoClient> (n3, "10.1.2.4", port,
22.14 - 100, Seconds(.01), 1024);
22.15 + Ptr<UdpEchoClient> client0 = CreateObject<UdpEchoClient> (n0, "10.1.2.1",
22.16 + port, 100, Seconds(.01), 1024);
22.17 + Ptr<UdpEchoClient> client1 = CreateObject<UdpEchoClient> (n1, "10.1.2.2",
22.18 + port, 100, Seconds(.01), 1024);
22.19 + Ptr<UdpEchoClient> client2 = CreateObject<UdpEchoClient> (n2, "10.1.2.3",
22.20 + port, 100, Seconds(.01), 1024);
22.21 + Ptr<UdpEchoClient> client3 = CreateObject<UdpEchoClient> (n3, "10.1.2.4",
22.22 + port, 100, Seconds(.01), 1024);
22.23
22.24 Ptr<UdpEchoServer> server4 = CreateObject<UdpEchoServer> (n4, port);
22.25 Ptr<UdpEchoServer> server5 = CreateObject<UdpEchoServer> (n5, port);
23.1 --- a/tutorial/tutorial-point-to-point.cc Tue Feb 05 15:29:17 2008 -0500
23.2 +++ b/tutorial/tutorial-point-to-point.cc Tue Feb 05 15:30:16 2008 -0500
23.3 @@ -58,8 +58,8 @@
23.4
23.5 uint16_t port = 7;
23.6
23.7 - Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2", port,
23.8 - 1, Seconds(1.), 1024);
23.9 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
23.10 + port, 1, Seconds(1.), 1024);
23.11
23.12 Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
23.13
24.1 --- a/tutorial/tutorial-star-routing.cc Tue Feb 05 15:29:17 2008 -0500
24.2 +++ b/tutorial/tutorial-star-routing.cc Tue Feb 05 15:30:16 2008 -0500
24.3 @@ -145,8 +145,8 @@
24.4
24.5 uint16_t port = 7;
24.6
24.7 - Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n4, "10.1.1.2", port,
24.8 - 1, Seconds(1.), 1024);
24.9 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n4, "10.1.1.2",
24.10 + port, 1, Seconds(1.), 1024);
24.11
24.12 Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
24.13
25.1 --- a/tutorial/tutorial-star.cc Tue Feb 05 15:29:17 2008 -0500
25.2 +++ b/tutorial/tutorial-star.cc Tue Feb 05 15:30:16 2008 -0500
25.3 @@ -145,8 +145,8 @@
25.4
25.5 uint16_t port = 7;
25.6
25.7 - Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2", port,
25.8 - 1, Seconds(1.), 1024);
25.9 + Ptr<UdpEchoClient> client = CreateObject<UdpEchoClient> (n0, "10.1.1.2",
25.10 + port, 1, Seconds(1.), 1024);
25.11
25.12 Ptr<UdpEchoServer> server = CreateObject<UdpEchoServer> (n1, port);
25.13