Help with Callback

1,263 views
Skip to first unread message

Konstantinos

unread,
Mar 8, 2011, 8:37:58 AM3/8/11
to ns-3-...@googlegroups.com
Hey,

I want to monitor the dropped packets at the MAC layer from the routing protocol that I have implemented.
I read that ns3::WifiMac has this MacRxDrop trace source so I tried to implement a callback using this trace.

This is what I have done :

Config::Connect ("/NodeList/*/$ns3::WifiMac/MacRxDrop", MakeBoundCallback (&MacRxDrop));

and I have this method inside my routing protocol for testing:
void RoutingProtocol::MacRxDrop(){
 std::cout << "MacRxDrop called";
}

When I compile this I get an error that Config is not declared. I have ns3/traced-callback.h included.

Another question regarding callbacks is the ns3::queue

ns3::Queue

  • Enqueue: Enqueue a packet in the queue.
  • Dequeue: Dequeue a packet from the queue.
  • Drop: Drop a packet stored in the queue.
Is this the queue at Application Layer or somewhere else?
Message has been deleted

Konstantinos

unread,
Mar 10, 2011, 10:17:43 AM3/10/11
to ns-3-...@googlegroups.com
I finally managed to get it compiled but it didn't work.

I use this method to call it
Config::ConnectWithoutContext("$ns3::WifiMac/MacRx", MakeCallback(&MyMacRx));

where MyMacRx just prints a message. I should get this messages every time a packet was received, right? But I don't get anything.
Is there any specific 'place' where I must put this method?

The point is that I want to implement this inside my routing protocol but in which of all the methods should it be included ? I tried to use it inside the SetIpv4 and DoStart but none of these worked.

I though to get a pointer to the MAC layer that I use and connect the trace there like this :
    Ptr<WifiMac> _mac = m_ipv4->GetObject<ns3::WifiNetDevice>()->GetMac();
    _mac->TraceConnectWithoutContext("$ns3::WifiMac/MacRxDrop", MakeCallback(&MyMacRxDrop));

But this time I get a segmentation fault.

Julien Mineraud

unread,
Mar 10, 2011, 4:14:47 PM3/10/11
to ns-3-users
Hi,

try that

if (!_mac->TraceConnectWithoutContext ("MacRx",
MakeCallback
(&YourClass::MyMacRx, this)))
{
NS_FATAL_ERROR ("trace fail");
}

if you're not in a class
do

if (!_mac->TraceConnectWithoutContext ("MacRx",
MakeCallback (&MyMacRx)))
{
NS_FATAL_ERROR ("trace fail");
}

Regards

Julien

Konstantinos

unread,
Mar 10, 2011, 6:46:46 PM3/10/11
to ns-3-...@googlegroups.com
Thank you for your answer. I tried it but now I'm getting a segm. fault.

It seems that I can't get the WifiNetDevice.

Ptr <WifiNetDevice> _device = m_ipv4->GetObject<WifiNetDevice>();

returns NULL at _device.
So, how can I get a pointer to WifiMac or WifiNetDevice inside the routing protocol?

Taral Shah

unread,
Mar 11, 2011, 12:13:47 PM3/11/11
to ns-3-...@googlegroups.com
hi Konstntinios,
 
make sure to use Mac helper in side your network. you can check fifth.cc program inside tutorial . They are giving example of packetsink helper. You have to use appropriate helper by looking at the ns-3 documentation(doxygen).
 
Regards,
Taral

--
You received this message because you are subscribed to the Google Groups "ns-3-users" group.
To post to this group, send email to ns-3-...@googlegroups.com.
To unsubscribe from this group, send email to ns-3-users+...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/ns-3-users?hl=en.

Konstantinos

unread,
Mar 15, 2011, 7:24:54 AM3/15/11
to ns-3-...@googlegroups.com
Hi  Taral,

Sorry for the late response. I have seen the fifth tutorial but I have a completely different situation here.
In this tutorial they want to use the trace in their script. In the same file they instantiate TCP etc.
What I want to do is to use the trace inside a module that I have created. It will look like a 'cross-layer' implementation.
In my test script I have a Wifi helper and a NQosMacHelper instantiated.
Do you suggest that I must first get a pointer to these with something like :
Ptr <WifiHelper> wifi_helper = m_ipv4->GetObject<WifiHelper>();
and then use this helper to get the device, mac etc ???

Regards
Konstantinos

Konstantinos

unread,
Mar 15, 2011, 11:15:25 AM3/15/11
to ns-3-...@googlegroups.com
Taking a pointer to the helper didn't not work.
Also there isn't a function to get a reference to the MAC from it.

alessandro paganelli

unread,
Mar 15, 2011, 12:11:10 PM3/15/11
to ns-3-users
Hi Konstantinos,

I have a very similar problem: I want to monitor a WiMAX subscriber
station's queue to find out where the packet losses actually happen in
my simulated network.
However, every attempt to connect the callback with the trace source
fails (well, it simply does nothing).

I used the Config::Connect statement instead of the TraceConnect one.
In particular, I want to monitor the "Drop" trace source of a
WimaxMacQueue object, so I used the following instruction:

Config::Connect ("/NodeList/1/DeviceList/
0/$ns3::SubscriberStationNetDevice/BasicConnection/TxQueue/Enqueue",
MakeCallback (&MacEnqueueCallback));

but it does not work at all. Where can I find the mistake? I found the
"connect string/path" a little bit confusing, eg: I found that the
parameter I wish to monitor can also be reached via the following:

/NodeList/[i]/DeviceList/[i]/$ns3::UanNetDevice/Channel/NoiseModel/
$ns3::SubscriberStationNetDevice/BasicConnection/TxQueue

but... why a WiMAX queue should be reached via a UanNetDevice???

I hope someone can help us!

Regards,
Alessandro

Konstantinos

unread,
Mar 15, 2011, 12:55:38 PM3/15/11
to ns-3-...@googlegroups.com
Hi Alessandro,

I also have tried the Config:Connect both in my script and in the network module.
For the first it worked but I want it inside my module to use it somehow.

I have this in both files changing only the m_node->GetId() with '*' for the script:

oss << "/NodeList/" << m_node->GetId() << "/DeviceList/*/Mac/$ns3::WifiMac/Tx";
Config::ConnectWithoutContext(oss.str(),MakeCallback(&MacRxDrop));

But it doesn't work inside the nework module. Perhaps I have to use a different path but I don't really know what to do.
The documentation is a little bit blur.

As far as your question is concerned, I think the two queues are different but they have similar implementation (names) for the trace because they do similar operations.

Konstantinos

unread,
Mar 15, 2011, 7:44:58 PM3/15/11
to ns-3-...@googlegroups.com
I managed to call my method inside the routing protocol using this line:
  Config::ConnectWithoutContext("/NodeList/*/DeviceList/*/Mac/$ns3::WifiMac/MacRxDrop",
      MakeCallback(&ns3::clwpr::RoutingProtocol::MacRxDrop));

Where MacRxDrop is:
void RoutingProtocol::MacRxDrop(Ptr <const Packet> p){
  std::cout << "MacRxDrop called at CLWPR for node\n";
}

My question now is: using the * for nodelist, this callback is connected to each node right? So if it is called for node #0, will MacRxDrop from node #1 be called ? Or there is one-to-one relation? If it is the second.. its ok. I'm in good path.

Another problem that I'm facing is that this MacRxDrop is a static method (need to be by the callback) but I want to increase a counter each time I call it. Something like m_dropPackets++; If I try to do this I get an error that I can't change m_dropPackets.

Regards

alessandro paganelli

unread,
Mar 16, 2011, 2:17:11 PM3/16/11
to ns-3-users
Hi Konstantinos,

if you use the * in the nodelist you will attach the callback to every
node that match what follows.
For instance, if you use:

Config::ConnectWithoutContext("/NodeList/*/DeviceList/*/Mac/
$ns3::WifiMac/M acRxDrop",
MakeCallback(&ns3::clwpr::RoutingProtocol::MacRxDrop));

you are going to attach the callback to every node of you network that
has a device that has aggregated a WifiMac object.
If there is a Csma node, it will not be affected by this Connect.

For the last question, I adopted a very bad programming technique for
a situation very close to your one: I declared a global variable that
can be managed by the callback.
I used this solution only for quick debug and I guess that there are
"cleaner" methods to make this.

Regards,
Alessandro

On 16 Mar, 00:44, Konstantinos <dinos.katsa...@gmail.com> wrote:
> I managed to call my method inside the routing protocol using this line:
>
> Config::ConnectWithoutContext("/NodeList/*/DeviceList/*/Mac/$ns3::WifiMac/M acRxDrop",

Taral Shah

unread,
Mar 16, 2011, 10:03:06 PM3/16/11
to ns-3-...@googlegroups.com
Hi ,

Sorry for late response.

Konstantinos 

/NodeList/*/DeviceList/*/Mac/

you have to replace node on which you want to monitor RxDrop. and Make sure you are installing proper protocol on proper node link.

I did same thing for sinking packet using packetsink helper. and I am installing Onoff helper application on node1-7 interface and I am monitoring packet on node 7.
ns3::OnOffHelper::OnOffHelper(std::string  protocol,
Address  address 
)


Taral Shah

unread,
Mar 16, 2011, 10:04:40 PM3/16/11
to ns-3-...@googlegroups.com, alessandro paganelli
hi alessandro,

Hey How you defined global variable in ns-3. can you tell me!! I have to do it in my network.

Thanks,
Taral

On Wed, Mar 16, 2011 at 11:17 AM, alessandro paganelli <alessandro...@gmail.com> wrote:

alessandro paganelli

unread,
Mar 17, 2011, 5:53:23 AM3/17/11
to ns-3-users
Hi Taral,

I declared the variable I needed (i.e. int nSentPacket; ) outside the
main function, before the declaration of the other functions I used in
my program (that is, immediately after the "using namespace ns3;"
instruction).

Regards,
Alessandro

Konstantinos

unread,
Mar 17, 2011, 10:37:43 AM3/17/11
to ns-3-...@googlegroups.com
Thanks for the reply Taral.

I have found that also my self. But my problem/question still remains.

I want to install a callback at my routing protocol in order to monitor the dropped packets and other useful measurements from MAC/PHY layers. So this should be done for EVERY node separately. If a node drops a packet at some point in MAC/PHY, the network layer (my routing protocol) should be informed in order to increase a counter.

That's what I want to do.

Taral.vigour

unread,
Mar 17, 2011, 11:15:00 AM3/17/11
to ns-3-...@googlegroups.com
Hey alessandro

I want to define global value for pointer I did same way as you mention but it's giving me zero value in main function.

For integer it works fine

Thanks for reply.

Regards
Taral

alessandro paganelli

unread,
Mar 17, 2011, 1:44:31 PM3/17/11
to ns-3-users
Hi Taral,

after the declaration of the pointer, outside the main function, you
have an undefined pointer, that is, it may point to a memory area that
is not under your control. After the declaration, you must define it
by setting a regular value to it. You can do this inside the main
function, in the same way in which you assign a value to a pointer
declared as usual.
The difference between the pointer declared inside the main and the
global one is that the latter can be accessed also by the callback
functions you define. This is because the "scope" of the global
variable is, as the name suggests, global (in other words, it can be
"seen" by every function of your program that you define in the same
source file of the global variable).

Kind regards,
Alessandro

On 17 Mar, 16:15, " Taral.vigour" <taral.vig...@gmail.com> wrote:
> Hey alessandro
>
> I want to define global value for pointer I did same way as you mention but it's giving me zero value in main function.
>
> For integer it works fine
>
> Thanks for reply.
>
> Regards
> Taral
>
Reply all
Reply to author
Forward
0 new messages