Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 1 | // Copyright (c) 2013 The Chromium OS Authors. All rights reserved. |
| 2 | // Use of this source code is governed by a BSD-style license that can be |
| 3 | // found in the LICENSE file. |
| 4 | |
| 5 | #include "shill/traffic_monitor.h" |
| 6 | |
| 7 | #include <base/bind.h> |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 8 | #include <base/stringprintf.h> |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 9 | #include <gtest/gtest.h> |
| 10 | |
| 11 | #include "shill/mock_device.h" |
| 12 | #include "shill/mock_event_dispatcher.h" |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 13 | #include "shill/mock_ipconfig.h" |
| 14 | #include "shill/mock_socket_info_reader.h" |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 15 | #include "shill/nice_mock_control.h" |
| 16 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 17 | using base::Bind; |
| 18 | using base::StringPrintf; |
| 19 | using base::Unretained; |
| 20 | using std::string; |
| 21 | using std::vector; |
| 22 | using testing::_; |
| 23 | using testing::Mock; |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 24 | using testing::NiceMock; |
| 25 | using testing::Return; |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 26 | using testing::ReturnRef; |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 27 | using testing::Test; |
| 28 | |
| 29 | namespace shill { |
| 30 | |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 31 | class TrafficMonitorTest : public Test { |
| 32 | public: |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 33 | static const string kLocalIpAddr; |
| 34 | static const uint16 kLocalPort1; |
| 35 | static const uint16 kLocalPort2; |
| 36 | static const uint16 kLocalPort3; |
| 37 | static const uint16 kLocalPort4; |
| 38 | static const uint16 kLocalPort5; |
| 39 | static const string kRemoteIpAddr; |
| 40 | static const uint16 kRemotePort; |
| 41 | static const uint64 kTxQueueLength1; |
| 42 | static const uint64 kTxQueueLength2; |
| 43 | static const uint64 kTxQueueLength3; |
| 44 | static const uint64 kTxQueueLength4; |
| 45 | |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 46 | TrafficMonitorTest() |
| 47 | : device_(new MockDevice(&control_, |
| 48 | &dispatcher_, |
| 49 | reinterpret_cast<Metrics *>(NULL), |
| 50 | reinterpret_cast<Manager *>(NULL), |
| 51 | "netdev0", |
| 52 | "00:11:22:33:44:55", |
| 53 | 1)), |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 54 | ipconfig_(new MockIPConfig(&control_, "netdev0")), |
| 55 | mock_socket_info_reader_(new MockSocketInfoReader), |
| 56 | monitor_(device_, &dispatcher_), |
| 57 | local_addr_(IPAddress::kFamilyIPv4), |
| 58 | remote_addr_(IPAddress::kFamilyIPv4) { |
| 59 | local_addr_.SetAddressFromString(kLocalIpAddr); |
| 60 | remote_addr_.SetAddressFromString(kRemoteIpAddr); |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 61 | } |
| 62 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 63 | MOCK_METHOD0(OnNoOutgoingPackets, void()); |
| 64 | |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 65 | protected: |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 66 | virtual void SetUp() { |
| 67 | monitor_.socket_info_reader_.reset( |
| 68 | mock_socket_info_reader_); // Passes ownership |
| 69 | |
| 70 | ipconfig_properties_.address = kLocalIpAddr; |
| 71 | EXPECT_CALL(*ipconfig_.get(), properties()) |
| 72 | .WillRepeatedly(ReturnRef(ipconfig_properties_)); |
| 73 | EXPECT_CALL(*device_.get(), ipconfig()) |
| 74 | .WillRepeatedly(ReturnRef(ipconfig_)); |
| 75 | } |
| 76 | |
| 77 | void VerifyStopped() { |
| 78 | EXPECT_TRUE(monitor_.sample_traffic_callback_.IsCancelled()); |
| 79 | EXPECT_EQ(0, monitor_.accummulated_failure_samples_); |
| 80 | } |
| 81 | |
| 82 | void VerifyStarted() { |
| 83 | EXPECT_FALSE(monitor_.sample_traffic_callback_.IsCancelled()); |
| 84 | } |
| 85 | |
| 86 | void SetupMockSocketInfos(const vector<SocketInfo> &socket_infos) { |
| 87 | mock_socket_infos_ = socket_infos; |
| 88 | EXPECT_CALL(*mock_socket_info_reader_, LoadTcpSocketInfo(_)) |
| 89 | .WillRepeatedly( |
| 90 | Invoke(this, &TrafficMonitorTest::MockLoadTcpSocketInfo)); |
| 91 | } |
| 92 | |
| 93 | bool MockLoadTcpSocketInfo(vector<SocketInfo> *info_list) { |
| 94 | *info_list = mock_socket_infos_; |
| 95 | return true; |
| 96 | } |
| 97 | |
| 98 | string FormatIPPort(const IPAddress &ip, const uint16 port) { |
| 99 | return StringPrintf("%s:%d", ip.ToString().c_str(), port); |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 100 | } |
| 101 | |
| 102 | NiceMockControl control_; |
| 103 | NiceMock<MockEventDispatcher> dispatcher_; |
| 104 | scoped_refptr<MockDevice> device_; |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 105 | scoped_refptr<MockIPConfig> ipconfig_; |
| 106 | IPConfig::Properties ipconfig_properties_; |
| 107 | MockSocketInfoReader *mock_socket_info_reader_; |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 108 | TrafficMonitor monitor_; |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 109 | vector<SocketInfo> mock_socket_infos_; |
| 110 | IPAddress local_addr_; |
| 111 | IPAddress remote_addr_; |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 112 | }; |
| 113 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 114 | // static |
| 115 | const string TrafficMonitorTest::kLocalIpAddr = "127.0.0.1"; |
| 116 | const uint16 TrafficMonitorTest::kLocalPort1 = 1234; |
| 117 | const uint16 TrafficMonitorTest::kLocalPort2 = 2345; |
| 118 | const uint16 TrafficMonitorTest::kLocalPort3 = 3456; |
| 119 | const uint16 TrafficMonitorTest::kLocalPort4 = 4567; |
| 120 | const uint16 TrafficMonitorTest::kLocalPort5 = 4567; |
| 121 | const string TrafficMonitorTest::kRemoteIpAddr = "192.168.1.1"; |
| 122 | const uint16 TrafficMonitorTest::kRemotePort = 5678; |
| 123 | const uint64 TrafficMonitorTest::kTxQueueLength1 = 111; |
| 124 | const uint64 TrafficMonitorTest::kTxQueueLength2 = 222; |
| 125 | const uint64 TrafficMonitorTest::kTxQueueLength3 = 333; |
| 126 | const uint64 TrafficMonitorTest::kTxQueueLength4 = 444; |
| 127 | |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 128 | TEST_F(TrafficMonitorTest, StartAndStop) { |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 129 | // Stop without start |
| 130 | monitor_.Stop(); |
| 131 | VerifyStopped(); |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 132 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 133 | // Normal start |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 134 | monitor_.Start(); |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 135 | VerifyStarted(); |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 136 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 137 | // Stop after start |
| 138 | monitor_.Stop(); |
| 139 | VerifyStopped(); |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 140 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 141 | // Stop again without start |
| 142 | monitor_.Stop(); |
| 143 | VerifyStopped(); |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 144 | } |
| 145 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 146 | TEST_F(TrafficMonitorTest, BuildIPPortToTxQueueLengthValid) { |
| 147 | vector<SocketInfo> socket_infos; |
| 148 | socket_infos.push_back( |
| 149 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 150 | local_addr_, |
| 151 | TrafficMonitorTest::kLocalPort1, |
| 152 | remote_addr_, |
| 153 | TrafficMonitorTest::kRemotePort, |
| 154 | TrafficMonitorTest::kTxQueueLength1, |
| 155 | 0, |
| 156 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 157 | TrafficMonitor::IPPortToTxQueueLengthMap tx_queue_lengths; |
| 158 | monitor_.BuildIPPortToTxQueueLength(socket_infos, &tx_queue_lengths); |
| 159 | EXPECT_EQ(1, tx_queue_lengths.size()); |
| 160 | string ip_port = FormatIPPort(local_addr_, TrafficMonitorTest::kLocalPort1); |
| 161 | EXPECT_EQ(TrafficMonitorTest::kTxQueueLength1, tx_queue_lengths[ip_port]); |
| 162 | } |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 163 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 164 | TEST_F(TrafficMonitorTest, BuildIPPortToTxQueueLengthInvalidDevice) { |
| 165 | vector<SocketInfo> socket_infos; |
| 166 | IPAddress foreign_ip_addr(IPAddress::kFamilyIPv4); |
| 167 | foreign_ip_addr.SetAddressFromString("192.167.1.1"); |
| 168 | socket_infos.push_back( |
| 169 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 170 | foreign_ip_addr, |
| 171 | TrafficMonitorTest::kLocalPort1, |
| 172 | remote_addr_, |
| 173 | TrafficMonitorTest::kRemotePort, |
| 174 | TrafficMonitorTest::kTxQueueLength1, |
| 175 | 0, |
| 176 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 177 | TrafficMonitor::IPPortToTxQueueLengthMap tx_queue_lengths; |
| 178 | monitor_.BuildIPPortToTxQueueLength(socket_infos, &tx_queue_lengths); |
| 179 | EXPECT_EQ(0, tx_queue_lengths.size()); |
| 180 | } |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 181 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 182 | TEST_F(TrafficMonitorTest, BuildIPPortToTxQueueLengthZero) { |
| 183 | vector<SocketInfo> socket_infos; |
| 184 | socket_infos.push_back( |
| 185 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 186 | local_addr_, |
| 187 | TrafficMonitorTest::kLocalPort1, |
| 188 | remote_addr_, |
| 189 | TrafficMonitorTest::kRemotePort, |
| 190 | 0, |
| 191 | 0, |
| 192 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 193 | TrafficMonitor::IPPortToTxQueueLengthMap tx_queue_lengths; |
| 194 | monitor_.BuildIPPortToTxQueueLength(socket_infos, &tx_queue_lengths); |
| 195 | EXPECT_EQ(0, tx_queue_lengths.size()); |
| 196 | } |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 197 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 198 | TEST_F(TrafficMonitorTest, BuildIPPortToTxQueueLengthInvalidConnectionState) { |
| 199 | vector<SocketInfo> socket_infos; |
| 200 | socket_infos.push_back( |
| 201 | SocketInfo(SocketInfo::kConnectionStateSynSent, |
| 202 | local_addr_, |
| 203 | TrafficMonitorTest::kLocalPort1, |
| 204 | remote_addr_, |
| 205 | TrafficMonitorTest::kRemotePort, |
| 206 | TrafficMonitorTest::kTxQueueLength1, |
| 207 | 0, |
| 208 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 209 | TrafficMonitor::IPPortToTxQueueLengthMap tx_queue_lengths; |
| 210 | monitor_.BuildIPPortToTxQueueLength(socket_infos, &tx_queue_lengths); |
| 211 | EXPECT_EQ(0, tx_queue_lengths.size()); |
| 212 | } |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 213 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 214 | TEST_F(TrafficMonitorTest, BuildIPPortToTxQueueLengthInvalidTimerState) { |
| 215 | vector<SocketInfo> socket_infos; |
| 216 | socket_infos.push_back( |
| 217 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 218 | local_addr_, |
| 219 | TrafficMonitorTest::kLocalPort1, |
| 220 | remote_addr_, |
| 221 | TrafficMonitorTest::kRemotePort, |
| 222 | TrafficMonitorTest::kTxQueueLength1, |
| 223 | 0, |
| 224 | SocketInfo::kTimerStateNoTimerPending)); |
| 225 | TrafficMonitor::IPPortToTxQueueLengthMap tx_queue_lengths; |
| 226 | monitor_.BuildIPPortToTxQueueLength(socket_infos, &tx_queue_lengths); |
| 227 | EXPECT_EQ(0, tx_queue_lengths.size()); |
| 228 | } |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 229 | |
Thieu Le | 0302666 | 2013-04-04 10:45:11 -0700 | [diff] [blame] | 230 | TEST_F(TrafficMonitorTest, BuildIPPortToTxQueueLengthMultipleEntries) { |
| 231 | vector<SocketInfo> socket_infos; |
| 232 | socket_infos.push_back( |
| 233 | SocketInfo(SocketInfo::kConnectionStateSynSent, |
| 234 | local_addr_, |
| 235 | TrafficMonitorTest::kLocalPort1, |
| 236 | remote_addr_, |
| 237 | TrafficMonitorTest::kRemotePort, |
| 238 | TrafficMonitorTest::kTxQueueLength1, |
| 239 | 0, |
| 240 | SocketInfo::kTimerStateNoTimerPending)); |
| 241 | socket_infos.push_back( |
| 242 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 243 | local_addr_, |
| 244 | TrafficMonitorTest::kLocalPort2, |
| 245 | remote_addr_, |
| 246 | TrafficMonitorTest::kRemotePort, |
| 247 | TrafficMonitorTest::kTxQueueLength2, |
| 248 | 0, |
| 249 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 250 | socket_infos.push_back( |
| 251 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 252 | local_addr_, |
| 253 | TrafficMonitorTest::kLocalPort3, |
| 254 | remote_addr_, |
| 255 | TrafficMonitorTest::kRemotePort, |
| 256 | TrafficMonitorTest::kTxQueueLength3, |
| 257 | 0, |
| 258 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 259 | socket_infos.push_back( |
| 260 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 261 | local_addr_, |
| 262 | TrafficMonitorTest::kLocalPort4, |
| 263 | remote_addr_, |
| 264 | TrafficMonitorTest::kRemotePort, |
| 265 | TrafficMonitorTest::kTxQueueLength4, |
| 266 | 0, |
| 267 | SocketInfo::kTimerStateNoTimerPending)); |
| 268 | socket_infos.push_back( |
| 269 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 270 | local_addr_, |
| 271 | TrafficMonitorTest::kLocalPort5, |
| 272 | remote_addr_, |
| 273 | TrafficMonitorTest::kRemotePort, |
| 274 | 0, |
| 275 | 0, |
| 276 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 277 | TrafficMonitor::IPPortToTxQueueLengthMap tx_queue_lengths; |
| 278 | monitor_.BuildIPPortToTxQueueLength(socket_infos, &tx_queue_lengths); |
| 279 | EXPECT_EQ(2, tx_queue_lengths.size()); |
| 280 | string ip_port = FormatIPPort(local_addr_, TrafficMonitorTest::kLocalPort2); |
| 281 | EXPECT_EQ(kTxQueueLength2, tx_queue_lengths[ip_port]); |
| 282 | ip_port = FormatIPPort(local_addr_, TrafficMonitorTest::kLocalPort3); |
| 283 | EXPECT_EQ(kTxQueueLength3, tx_queue_lengths[ip_port]); |
| 284 | } |
| 285 | |
| 286 | TEST_F(TrafficMonitorTest, SampleTrafficStuckTxQueueSameQueueLength) { |
| 287 | vector<SocketInfo> socket_infos; |
| 288 | socket_infos.push_back( |
| 289 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 290 | local_addr_, |
| 291 | TrafficMonitorTest::kLocalPort1, |
| 292 | remote_addr_, |
| 293 | TrafficMonitorTest::kRemotePort, |
| 294 | TrafficMonitorTest::kTxQueueLength1, |
| 295 | 0, |
| 296 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 297 | SetupMockSocketInfos(socket_infos); |
| 298 | monitor_.set_tcp_out_traffic_not_routed_callback( |
| 299 | Bind(&TrafficMonitorTest::OnNoOutgoingPackets, Unretained(this))); |
| 300 | EXPECT_CALL(*this, OnNoOutgoingPackets()).Times(0); |
| 301 | monitor_.SampleTraffic(); |
| 302 | Mock::VerifyAndClearExpectations(this); |
| 303 | |
| 304 | // Mimic same queue length by using same mock socket info. |
| 305 | EXPECT_CALL(*this, OnNoOutgoingPackets()); |
| 306 | monitor_.SampleTraffic(); |
| 307 | Mock::VerifyAndClearExpectations(this); |
| 308 | |
| 309 | // Perform another sampling pass and make sure the callback is only |
| 310 | // triggered once. |
| 311 | EXPECT_CALL(*this, OnNoOutgoingPackets()).Times(0); |
| 312 | monitor_.SampleTraffic(); |
| 313 | } |
| 314 | |
| 315 | TEST_F(TrafficMonitorTest, SampleTrafficStuckTxQueueIncreasingQueueLength) { |
| 316 | vector<SocketInfo> socket_infos; |
| 317 | socket_infos.push_back( |
| 318 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 319 | local_addr_, |
| 320 | TrafficMonitorTest::kLocalPort1, |
| 321 | remote_addr_, |
| 322 | TrafficMonitorTest::kRemotePort, |
| 323 | TrafficMonitorTest::kTxQueueLength1, |
| 324 | 0, |
| 325 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 326 | SetupMockSocketInfos(socket_infos); |
| 327 | monitor_.set_tcp_out_traffic_not_routed_callback( |
| 328 | Bind(&TrafficMonitorTest::OnNoOutgoingPackets, Unretained(this))); |
| 329 | EXPECT_CALL(*this, OnNoOutgoingPackets()).Times(0); |
| 330 | monitor_.SampleTraffic(); |
| 331 | Mock::VerifyAndClearExpectations(this); |
| 332 | |
| 333 | socket_infos.clear(); |
| 334 | socket_infos.push_back( |
| 335 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 336 | local_addr_, |
| 337 | TrafficMonitorTest::kLocalPort1, |
| 338 | remote_addr_, |
| 339 | TrafficMonitorTest::kRemotePort, |
| 340 | TrafficMonitorTest::kTxQueueLength1 + 1, |
| 341 | 0, |
| 342 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 343 | SetupMockSocketInfos(socket_infos); |
| 344 | EXPECT_CALL(*this, OnNoOutgoingPackets()); |
| 345 | monitor_.SampleTraffic(); |
| 346 | } |
| 347 | |
| 348 | TEST_F(TrafficMonitorTest, SampleTrafficStuckTxQueueVariousQueueLengths) { |
| 349 | vector<SocketInfo> socket_infos; |
| 350 | socket_infos.push_back( |
| 351 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 352 | local_addr_, |
| 353 | TrafficMonitorTest::kLocalPort1, |
| 354 | remote_addr_, |
| 355 | TrafficMonitorTest::kRemotePort, |
| 356 | TrafficMonitorTest::kTxQueueLength2, |
| 357 | 0, |
| 358 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 359 | SetupMockSocketInfos(socket_infos); |
| 360 | monitor_.set_tcp_out_traffic_not_routed_callback( |
| 361 | Bind(&TrafficMonitorTest::OnNoOutgoingPackets, Unretained(this))); |
| 362 | EXPECT_CALL(*this, OnNoOutgoingPackets()).Times(0); |
| 363 | monitor_.SampleTraffic(); |
| 364 | Mock::VerifyAndClearExpectations(this); |
| 365 | |
| 366 | socket_infos.clear(); |
| 367 | socket_infos.push_back( |
| 368 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 369 | local_addr_, |
| 370 | TrafficMonitorTest::kLocalPort1, |
| 371 | remote_addr_, |
| 372 | TrafficMonitorTest::kRemotePort, |
| 373 | TrafficMonitorTest::kTxQueueLength1, |
| 374 | 0, |
| 375 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 376 | SetupMockSocketInfos(socket_infos); |
| 377 | EXPECT_CALL(*this, OnNoOutgoingPackets()).Times(0); |
| 378 | monitor_.SampleTraffic(); |
| 379 | Mock::VerifyAndClearExpectations(this); |
| 380 | |
| 381 | socket_infos.clear(); |
| 382 | socket_infos.push_back( |
| 383 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 384 | local_addr_, |
| 385 | TrafficMonitorTest::kLocalPort1, |
| 386 | remote_addr_, |
| 387 | TrafficMonitorTest::kRemotePort, |
| 388 | TrafficMonitorTest::kTxQueueLength2, |
| 389 | 0, |
| 390 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 391 | SetupMockSocketInfos(socket_infos); |
| 392 | EXPECT_CALL(*this, OnNoOutgoingPackets()); |
| 393 | monitor_.SampleTraffic(); |
| 394 | } |
| 395 | |
| 396 | TEST_F(TrafficMonitorTest, SampleTrafficUnstuckTxQueueZeroQueueLength) { |
| 397 | vector<SocketInfo> socket_infos; |
| 398 | socket_infos.push_back( |
| 399 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 400 | local_addr_, |
| 401 | TrafficMonitorTest::kLocalPort1, |
| 402 | remote_addr_, |
| 403 | TrafficMonitorTest::kRemotePort, |
| 404 | TrafficMonitorTest::kTxQueueLength1, |
| 405 | 0, |
| 406 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 407 | SetupMockSocketInfos(socket_infos); |
| 408 | monitor_.set_tcp_out_traffic_not_routed_callback( |
| 409 | Bind(&TrafficMonitorTest::OnNoOutgoingPackets, Unretained(this))); |
| 410 | EXPECT_CALL(*this, OnNoOutgoingPackets()).Times(0); |
| 411 | monitor_.SampleTraffic(); |
| 412 | |
| 413 | socket_infos.clear(); |
| 414 | socket_infos.push_back( |
| 415 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 416 | local_addr_, |
| 417 | TrafficMonitorTest::kLocalPort1, |
| 418 | remote_addr_, |
| 419 | TrafficMonitorTest::kRemotePort, |
| 420 | 0, |
| 421 | 0, |
| 422 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 423 | SetupMockSocketInfos(socket_infos); |
| 424 | monitor_.SampleTraffic(); |
| 425 | EXPECT_EQ(0, monitor_.accummulated_failure_samples_); |
| 426 | } |
| 427 | |
| 428 | TEST_F(TrafficMonitorTest, SampleTrafficUnstuckTxQueueNoConnection) { |
| 429 | vector<SocketInfo> socket_infos; |
| 430 | socket_infos.push_back( |
| 431 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 432 | local_addr_, |
| 433 | TrafficMonitorTest::kLocalPort1, |
| 434 | remote_addr_, |
| 435 | TrafficMonitorTest::kRemotePort, |
| 436 | TrafficMonitorTest::kTxQueueLength1, |
| 437 | 0, |
| 438 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 439 | SetupMockSocketInfos(socket_infos); |
| 440 | monitor_.set_tcp_out_traffic_not_routed_callback( |
| 441 | Bind(&TrafficMonitorTest::OnNoOutgoingPackets, Unretained(this))); |
| 442 | EXPECT_CALL(*this, OnNoOutgoingPackets()).Times(0); |
| 443 | monitor_.SampleTraffic(); |
| 444 | |
| 445 | socket_infos.clear(); |
| 446 | SetupMockSocketInfos(socket_infos); |
| 447 | monitor_.SampleTraffic(); |
| 448 | EXPECT_EQ(0, monitor_.accummulated_failure_samples_); |
| 449 | } |
| 450 | |
| 451 | TEST_F(TrafficMonitorTest, SampleTrafficUnstuckTxQueueStateChanged) { |
| 452 | vector<SocketInfo> socket_infos; |
| 453 | socket_infos.push_back( |
| 454 | SocketInfo(SocketInfo::kConnectionStateEstablished, |
| 455 | local_addr_, |
| 456 | TrafficMonitorTest::kLocalPort1, |
| 457 | remote_addr_, |
| 458 | TrafficMonitorTest::kRemotePort, |
| 459 | TrafficMonitorTest::kTxQueueLength1, |
| 460 | 0, |
| 461 | SocketInfo::kTimerStateRetransmitTimerPending)); |
| 462 | SetupMockSocketInfos(socket_infos); |
| 463 | monitor_.set_tcp_out_traffic_not_routed_callback( |
| 464 | Bind(&TrafficMonitorTest::OnNoOutgoingPackets, Unretained(this))); |
| 465 | EXPECT_CALL(*this, OnNoOutgoingPackets()).Times(0); |
| 466 | monitor_.SampleTraffic(); |
| 467 | |
| 468 | socket_infos.clear(); |
| 469 | socket_infos.push_back( |
| 470 | SocketInfo(SocketInfo::kConnectionStateClose, |
| 471 | local_addr_, |
| 472 | TrafficMonitorTest::kLocalPort1, |
| 473 | remote_addr_, |
| 474 | TrafficMonitorTest::kRemotePort, |
| 475 | 0, |
| 476 | 0, |
| 477 | SocketInfo::kTimerStateNoTimerPending)); |
| 478 | SetupMockSocketInfos(socket_infos); |
| 479 | monitor_.SampleTraffic(); |
| 480 | EXPECT_EQ(0, monitor_.accummulated_failure_samples_); |
Ben Chan | b061f89 | 2013-02-27 17:46:55 -0800 | [diff] [blame] | 481 | } |
| 482 | |
| 483 | } // namespace shill |