A Discrete-Event Network Simulator
API
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
packet-loss-counter.cc
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2009 INRIA, UDCAST
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License version 2 as
7  * published by the Free Software Foundation;
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17  *
18  * Author: Amine Ismail <amine.ismail@sophia.inria.fr>
19  * <amine.ismail@udcast.com>
20  */
21 
22 #include "ns3/log.h"
23 #include "ns3/simulator.h"
24 #include "ns3/uinteger.h"
25 #include "packet-loss-counter.h"
26 
27 namespace ns3 {
28 
29 NS_LOG_COMPONENT_DEFINE ("PacketLossCounter");
30 
31 
32 PacketLossCounter::PacketLossCounter (uint8_t bitmapSize)
33  : m_lost (0),
34  m_bitMapSize (0),
35  m_lastMaxSeqNum (0),
36  m_receiveBitMap (0)
37 {
38  NS_LOG_FUNCTION (this << bitmapSize);
39  SetBitMapSize (bitmapSize);
40 }
41 
42 PacketLossCounter::~PacketLossCounter ()
43 {
44  NS_LOG_FUNCTION (this);
45  delete [] m_receiveBitMap;
46 }
47 
48 uint16_t
49 PacketLossCounter::GetBitMapSize () const
50 {
51  NS_LOG_FUNCTION (this);
52  return m_bitMapSize * 8;
53 }
54 
55 void
56 PacketLossCounter::SetBitMapSize (uint16_t winSize)
57 {
58  NS_LOG_FUNCTION (this << winSize);
59 
60  NS_ASSERT_MSG (winSize%8==0,"The packet window size should be a multiple of 8");
61  m_bitMapSize = winSize/8;
62  if (m_receiveBitMap!=0)
63  {
64  delete [] m_receiveBitMap;
65  }
66  m_receiveBitMap = new uint8_t [m_bitMapSize] ();
67  memset (m_receiveBitMap,0xFF,m_bitMapSize);
68 }
69 
70 uint32_t
71 PacketLossCounter::GetLost () const
72 {
73  NS_LOG_FUNCTION (this);
74  return m_lost;
75 }
76 
77 bool
78 PacketLossCounter::GetBit (uint32_t seqNum)
79 {
80  NS_LOG_FUNCTION (this << seqNum);
81  return ((m_receiveBitMap[(seqNum%(m_bitMapSize*8))/8] >> (7-(seqNum%8)))&0x01);
82 }
83 
84 void
85 PacketLossCounter::SetBit (uint32_t seqNum, bool val)
86 {
87  NS_LOG_FUNCTION (this << seqNum << val);
88  if (val)
89  {
90  m_receiveBitMap[(seqNum%(m_bitMapSize*8))/8] |= 0x80 >> (seqNum%8);
91  }
92  else
93  {
94  m_receiveBitMap[(seqNum%(m_bitMapSize*8))/8] &= ~(0x80 >> (seqNum%8));
95  }
96 }
97 
98 /*
99  * This algo works as follows:
100  * When a packet is received:
101  * 1) From the last received packet to the current one:
102  * 1.1) check the corresponding bit in the bitMAP.
103  * This bit indicates if the packet with (SeqNum-bitMapSizeInBit) is
104  * received (1) or not (0)
105  * 1.2) Mark the packet as lost (0) in the bitMap
106  * 2) Mark the current packet as received (1) in the bitMap
107  * 3) Update the value of the last received packet
108  */
109 
110 void
111 PacketLossCounter::NotifyReceived (uint32_t seqNum)
112 {
113  NS_LOG_FUNCTION (this << seqNum);
114  for (uint32_t i=m_lastMaxSeqNum+1; i<=seqNum; i++)
115  {
116  if (GetBit (i)!=1)
117  {
118  NS_LOG_INFO ("Packet lost: " << i-(m_bitMapSize*8));
119  m_lost++;
120  }
121  SetBit (i, 0);
122  }
123  SetBit (seqNum, 1);
124  if (seqNum>m_lastMaxSeqNum)
125  {
126  m_lastMaxSeqNum = seqNum;
127  }
128 }
129 
130 } // namespace ns3
#define NS_LOG_FUNCTION(parameters)
Definition: log.h:311
#define NS_LOG_COMPONENT_DEFINE(name)
Definition: log.h:122
#define NS_LOG_INFO(msg)
Definition: log.h:264
#define NS_ASSERT_MSG(condition, message)
Definition: assert.h:86