[Ns-developers] Students, Sockets and Smart Pointers

craigdo@ee.washington.edu craigdo at ee.washington.edu
Fri Mar 28 11:30:14 PDT 2008


> > There's a discussion going on in the context of ns-3 bug 
> 154 that I think
> > deserves a wider distribution.
> >
> > Gustavo has reported a student who wrote some code to use 
> sockets directly
> > which I reproduce at the end of the message. [If you happen 
> to be the
> > student who wrote this code, I'm not pointing fingers at 
> you.  I'm more
> > pointing fingers at the developers (me too) who led you 
> down the path you
> > found yourself in.]
> 
> A couple quick comments:
> 
> - This doesn't look like a sockets API problem to me.  That code shows
>   a basic misunderstanding of the central paradigm:
> 
>   + There's a simulation context, the universe of the test
>   + Within that universe are Nodes, which simulate computers
>   + Nodes have NetDevices simulating network hardware
>   + Nodes have Application objects corresponding to normal programs
> 
> The problem seems akin to setting up a GUI in Qt or GTK, applying a
> very imperative-styled set of loops and functions, and complaining
> that nothing happens (Qt & GTK are almost entirely event driven).

That is what I'm saying.  There's an issue here that is much broader than
whether or not a socket closes when a smart pointer goes out of context.

> Craig, my reading of your first message here sounds like a new call
> for a sockets API that could be (nearly) dropped in transparently for
> the usual BSD sockets API.  That'd be awesome, but not for educational
> reasons.  People could use that to run legacy code in NS3.  But,
> they'd still have to do some sim setup.  More importantly, I would
> argue strongly that people get just as confused by usual network
> programming as this student seems to have gotten.  I argue that even
> presented w/ a more typical API, they would get just as confused if
> they kept expanding on the program, i.e. to implement a protocol.

Let me try this again.  We have a new set of helpers coming soon that use
simple stack-based C++ objects in order to allow people to build nodes,
devices, channels, install IP stacks, etc., without having to learn much of
anything about the low-level ns-3 API.  We make it easy for people to get a
network structure up and running without too much effort.

I noticed that this student, in order to move a single packet from one node
to another, found himself deep down inside low-level ns-3 API immediately
and he or she clearly wasn't ready to be there.  I observed that we haven't
thought about a notion similar to helpers that might apply to what happens
when the simulation is running -- that is, a simple familiar way for people
to do something beyond make topological structures.

It occurred to me that people are naturally drawn to sockets as an API if
only because that's what they learned first and they are almost universally
available.  If we provided a simple helper that allowed someone to send data
without having to understand the low level API, we could complete an
unfinished package -- we could allow people to do complete (albeit simple)
simulations quite easily.

It further occurred to me that there is a large but surprisingly subtle
difference between setup code that executes before

	Simulator::Run ()

and code that is expected to run during the simulation.  To most of us, I
think, the distinction is obvious.  I mean, there is a bunch of code in main
() that exists just to get things set up for the important part of the code,
which is all executed by that Run() call.  To someone unfamiliar with how
the simulator works, that run may not at all be obvious and the distinction
between setup time and run time not obvious.

I think we can, fairly easily, help this student out by providing a starting
point in the system that is more familiar to him or her (just like we made
the topology helper API more familiar by not using Ptr<X> all over) and
makes what is happening with setup and simulation more obvious within the
asynchronous/event structure of the ssytem.

> I would be uneasy encouraging people not to fit protocols into
> Application objects.  

I'm not suggesting that at all.

> Stuffing everything into essentially a very
> linear program from main() sounds like a recipe for disaster.  

I'm not suggesting that at all.

> Without
> some really silly fancyness, they'd still have to start the simulator,
> you'd have to figure out how to interleave their execution w/ events,
> etc.  I.e., worst case scenario I, Confused Student, am going to write
> a program that creates a bunch of nodes, then runs a bunch of while ()
> { sleep(1); send(packet); } loops "on each one," and complain bitterly
> when it doesn't work.

I'm saying we can can make life easier for unsophisticated people than
dumping them down into the low-level API in order to write their first
packet -- with a helper that can help them do something simple to get them
on the right track from the start.

> However, to alleviate some of that, what if there was an Application
> class, instances of which take & execute a given method?  So, I could
> write a couple methods representing programs to run on nodes and hand
> off to those instances to execute.  A helper could make the whole
> thing very simple, and avoid having to subclass Application.  There
> would still be problems though, like the loop above.  Without a full
> threading thing going on, you just can't do that much if people aren't
> working within the event framework.

I'm not suggesting that we abandon the asynchronous nature of the simulator.
I'm suggesting that we try to do something to ease people into the simulator
conceptually without the overhead of having to learn what is happening at a
low level.  I'm speaking more of something that acts like an application
helper that is active during the simulation, not during topology creation.
We advertize it as a simple starting point, it has a familiar sounding name
and familiar methods and does something real without stretching a new user
too much :

  UdpSocketHelper sh0 (c.Get(0));  // socket helper on node 0
  UdpSocketHelper sh1 (c.Get(1));  // socket helper on node 1

The constructors could add an event that called a run method that the user
overrides.  In the user-changeable methods, the goal would be to temporarily
hide things like,

  TypeId tid = TypeId::LookupByName ("ns3::Udp");
  Ptr<SocketFactory> socketFactory =
    GetNode ()->GetObject<SocketFactory> (tid);
  m_socket = socketFactory->CreateSocket ();

and

  m_socket->SetRecvCallback(MakeCallback(&SomeClass::Receive, this));

Until the user is more prepared to understand and deal with them.  I was
thinking along the lines of,

  MyUdpSocketHelper::Run (void)
  {
    m_sock = CreateSocket ();
    m_sock->Bind ();
    m_sock->Connect (InetSocketAddress (peerAddress, peerPort));

    ScheduleSendEvent(Seconds (1.));
  }

Here the only things that are exposed are familiar socket calls, and
something to schedule an event to kickstart the simulation.  The fact that
it is an event-based simulation is not hidden, but some of the details
regarding how to manage events are ... deferred so a newbie can focus on
what's important, and not have to understand what 

  m_sendEvent = Simulator::Schedule(dt, &UdpEchoClient::Send, this);

means quite yet.  The next bit is

  MyUdpSocketHelper::SendEvent (void)
  {
    m_sock->Send ("hello");
    ScheduleSendEvent(Seconds (1.));
  }

Again, there's nothing to distract from the essence of the simulation.

Finally there is a simple receive method, something like,

MyUdpSocketHelper::Receive(char *buffer, uint32_t buflen, const Ipv4Address
from)
{
  NS_LOG_FUNCTION;
  NS_LOG_INFO ("Received " << buflen << " bytes from " << from);
}

So I'm not talking about anything super-significant in terms of development
effort.  I'm not talking about changing the way the simulator works.  As
I've said, it's more of a small helper to ease someone into ns-3 and point
them in the right direction at the start.  Someone should be able to take
the socket helper and understand what it is doing at the highest level quite
easily.  Major simulator concepts are introduced with no baggage.  Once he
or she gets something working, s/he can begin to poke into the class itself
and see how the internals are working where the real ns-3 API is exposed.

I'm only pondering the helper concept extended to things that happen while
the simulation is running.

-- Craig






More information about the Ns-developers mailing list