Made TickTime immutable, rewrote tick utils to be fakeable.

BUG=

Review URL: https://webrtc-codereview.appspot.com/798004

git-svn-id: http://webrtc.googlecode.com/svn/trunk@3053 4adac7df-926f-26a2-2b94-8c16560cd09d
This commit is contained in:
phoglund@webrtc.org 2012-11-07 13:37:19 +00:00
parent 6e9890d1aa
commit 4cebe6cded
9 changed files with 103 additions and 35 deletions

View File

@ -69,7 +69,7 @@ TEST_F(VideoProcessingModuleTest, Deflickering)
ASSERT_EQ(0, _vpm->GetFrameStats(&stats, _videoFrame)); ASSERT_EQ(0, _vpm->GetFrameStats(&stats, _videoFrame));
ASSERT_EQ(0, _vpm->Deflickering(&_videoFrame, &stats)); ASSERT_EQ(0, _vpm->Deflickering(&_videoFrame, &stats));
t1 = TickTime::Now(); t1 = TickTime::Now();
accTicks += t1 - t0; accTicks += (t1 - t0);
if (runIdx == 0) if (runIdx == 0)
{ {

View File

@ -107,7 +107,7 @@ TEST_F(VideoProcessingModuleTest, Denoising)
t0 = TickTime::Now(); t0 = TickTime::Now();
ASSERT_GE(modifiedPixels = _vpm->Denoising(&_videoFrame), 0); ASSERT_GE(modifiedPixels = _vpm->Denoising(&_videoFrame), 0);
t1 = TickTime::Now(); t1 = TickTime::Now();
accTicks += t1 - t0; accTicks += (t1 - t0);
if (runIdx == 0) if (runIdx == 0)
{ {

View File

@ -14,7 +14,7 @@
#include "common_video/libyuv/include/webrtc_libyuv.h" #include "common_video/libyuv/include/webrtc_libyuv.h"
#include "system_wrappers/interface/tick_util.h" #include "system_wrappers/interface/tick_util.h"
#include "testsupport/fileutils.h" #include "test/testsupport/fileutils.h"
namespace webrtc { namespace webrtc {
@ -283,7 +283,7 @@ TEST_F(VideoProcessingModuleTest, Resampler)
// stop timer // stop timer
t1 = TickTime::Now(); t1 = TickTime::Now();
accTicks += t1 - t0; accTicks += (t1 - t0);
if (accTicks.Microseconds() < minRuntime || runIdx == 0) { if (accTicks.Microseconds() < minRuntime || runIdx == 0) {
minRuntime = accTicks.Microseconds(); minRuntime = accTicks.Microseconds();

View File

@ -32,9 +32,13 @@
namespace webrtc { namespace webrtc {
class TickInterval; class TickInterval;
// Class representing the current time. This class is immutable.
class TickTime class TickTime
{ {
public: public:
TickTime();
explicit TickTime(WebRtc_Word64 ticks);
// Current time in the tick domain. // Current time in the tick domain.
static TickTime Now(); static TickTime Now();
@ -44,6 +48,7 @@ public:
// Now in the time domain in us. // Now in the time domain in us.
static WebRtc_Word64 MicrosecondTimestamp(); static WebRtc_Word64 MicrosecondTimestamp();
// Returns the number of ticks in the tick domain.
WebRtc_Word64 Ticks() const; WebRtc_Word64 Ticks() const;
static WebRtc_Word64 MillisecondsToTicks(const WebRtc_Word64 ms); static WebRtc_Word64 MillisecondsToTicks(const WebRtc_Word64 ms);
@ -52,15 +57,28 @@ public:
// Returns a TickTime that is ticks later than the passed TickTime // Returns a TickTime that is ticks later than the passed TickTime
friend TickTime operator+(const TickTime lhs, const WebRtc_Word64 ticks); friend TickTime operator+(const TickTime lhs, const WebRtc_Word64 ticks);
TickTime& operator+=(const WebRtc_Word64& rhs); TickTime& operator+=(const WebRtc_Word64& ticks);
// Returns a TickInterval that is the difference in ticks beween rhs and lhs // Returns a TickInterval that is the difference in ticks beween rhs and lhs
friend TickInterval operator-(const TickTime& lhs, const TickTime& rhs); friend TickInterval operator-(const TickTime& lhs, const TickTime& rhs);
// Call to engage the fake clock. This is useful for tests since relying on
// a real clock often makes the test flaky.
static void UseFakeClock(WebRtc_Word64 start_millisecond);
// Advance the fake clock. Must be called after UseFakeClock.
static void AdvanceFakeClock(WebRtc_Word64 milliseconds);
private: private:
static WebRtc_Word64 QueryOsForTicks();
static bool _use_fake_clock;
static WebRtc_Word64 _fake_ticks;
WebRtc_Word64 _ticks; WebRtc_Word64 _ticks;
}; };
// Reperesents a time delta in ticks. This class is immutable.
class TickInterval class TickInterval
{ {
public: public:
@ -72,12 +90,12 @@ public:
// Returns the sum of two TickIntervals as a TickInterval // Returns the sum of two TickIntervals as a TickInterval
friend TickInterval operator+(const TickInterval& lhs, friend TickInterval operator+(const TickInterval& lhs,
const TickInterval& rhs); const TickInterval& rhs);
TickInterval& operator-=(const TickInterval& rhs); TickInterval& operator+=(const TickInterval& rhs);
// Returns a TickInterval corresponding to rhs - lhs // Returns a TickInterval corresponding to rhs - lhs
friend TickInterval operator-(const TickInterval& lhs, friend TickInterval operator-(const TickInterval& lhs,
const TickInterval& rhs); const TickInterval& rhs);
TickInterval& operator+=(const TickInterval& rhs); TickInterval& operator-=(const TickInterval& rhs);
friend bool operator>(const TickInterval& lhs, const TickInterval& rhs); friend bool operator>(const TickInterval& lhs, const TickInterval& rhs);
friend bool operator<=(const TickInterval& lhs, const TickInterval& rhs); friend bool operator<=(const TickInterval& lhs, const TickInterval& rhs);
@ -115,25 +133,44 @@ inline TickTime operator+(const TickTime lhs, const WebRtc_Word64 ticks)
time._ticks += ticks; time._ticks += ticks;
return time; return time;
} }
inline bool operator>(const TickInterval& lhs, const TickInterval& rhs) inline bool operator>(const TickInterval& lhs, const TickInterval& rhs)
{ {
return lhs._interval > rhs._interval; return lhs._interval > rhs._interval;
} }
inline bool operator<=(const TickInterval& lhs, const TickInterval& rhs) inline bool operator<=(const TickInterval& lhs, const TickInterval& rhs)
{ {
return lhs._interval <= rhs._interval; return lhs._interval <= rhs._interval;
} }
inline bool operator<(const TickInterval& lhs, const TickInterval& rhs) inline bool operator<(const TickInterval& lhs, const TickInterval& rhs)
{ {
return lhs._interval <= rhs._interval; return lhs._interval <= rhs._interval;
} }
inline bool operator>=(const TickInterval& lhs, const TickInterval& rhs) inline bool operator>=(const TickInterval& lhs, const TickInterval& rhs)
{ {
return lhs._interval >= rhs._interval; return lhs._interval >= rhs._interval;
} }
inline TickTime::TickTime()
: _ticks(0) {
}
inline TickTime::TickTime(WebRtc_Word64 ticks)
: _ticks(ticks) {
}
inline TickTime TickTime::Now() inline TickTime TickTime::Now()
{ {
if (_use_fake_clock)
return TickTime(_fake_ticks);
else
return TickTime(QueryOsForTicks());
}
inline WebRtc_Word64 TickTime::QueryOsForTicks() {
TickTime result; TickTime result;
#if _WIN32 #if _WIN32
// TODO(wu): Remove QueryPerformanceCounter implementation. // TODO(wu): Remove QueryPerformanceCounter implementation.
@ -159,7 +196,7 @@ inline TickTime TickTime::Now()
// threads. // threads.
// 0x0fffffff ~3.1 days, the code will not take that long to execute // 0x0fffffff ~3.1 days, the code will not take that long to execute
// so it must have been a wrap around. // so it must have been a wrap around.
if(old > 0xf0000000 && now < 0x0fffffff) if(old > 0xf0000000 && now < 0x0fffffff)
{ {
numWrapTimeGetTime++; numWrapTimeGetTime++;
} }
@ -198,43 +235,42 @@ inline TickTime TickTime::Now()
gettimeofday(&tv, NULL); gettimeofday(&tv, NULL);
result._ticks = 1000000LL * static_cast<WebRtc_Word64>(tv.tv_sec) + static_cast<WebRtc_Word64>(tv.tv_usec); result._ticks = 1000000LL * static_cast<WebRtc_Word64>(tv.tv_sec) + static_cast<WebRtc_Word64>(tv.tv_usec);
#endif #endif
return result; return result._ticks;
} }
inline WebRtc_Word64 TickTime::MillisecondTimestamp() inline WebRtc_Word64 TickTime::MillisecondTimestamp()
{ {
TickTime now = TickTime::Now(); WebRtc_Word64 ticks = TickTime::Now().Ticks();
#if _WIN32 #if _WIN32
#ifdef USE_QUERY_PERFORMANCE_COUNTER #ifdef USE_QUERY_PERFORMANCE_COUNTER
LARGE_INTEGER qpfreq; LARGE_INTEGER qpfreq;
QueryPerformanceFrequency(&qpfreq); QueryPerformanceFrequency(&qpfreq);
return (now._ticks * 1000) / qpfreq.QuadPart; return (ticks * 1000) / qpfreq.QuadPart;
#else #else
return now._ticks; return ticks;
#endif #endif
#elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC)
return now._ticks / 1000000LL; return ticks / 1000000LL;
#else #else
return now._ticks / 1000LL; return ticks / 1000LL;
#endif #endif
} }
inline WebRtc_Word64 TickTime::MicrosecondTimestamp() inline WebRtc_Word64 TickTime::MicrosecondTimestamp()
{ {
TickTime now = TickTime::Now(); WebRtc_Word64 ticks = TickTime::Now().Ticks();
#if _WIN32 #if _WIN32
#ifdef USE_QUERY_PERFORMANCE_COUNTER #ifdef USE_QUERY_PERFORMANCE_COUNTER
LARGE_INTEGER qpfreq; LARGE_INTEGER qpfreq;
QueryPerformanceFrequency(&qpfreq); QueryPerformanceFrequency(&qpfreq);
return (now._ticks * 1000) / (qpfreq.QuadPart/1000); return (ticks * 1000) / (qpfreq.QuadPart/1000);
#else #else
return now._ticks *1000LL; return ticks *1000LL;
#endif #endif
#elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC)
return now._ticks / 1000LL; return ticks / 1000LL;
#else #else
return now._ticks; return ticks;
#endif #endif
} }
@ -300,7 +336,7 @@ inline WebRtc_Word64 TickInterval::Milliseconds() const
QueryPerformanceFrequency(&qpfreq); QueryPerformanceFrequency(&qpfreq);
return (_interval * 1000) / qpfreq.QuadPart; return (_interval * 1000) / qpfreq.QuadPart;
#else #else
// _interval is in ms // _interval is in ms
return _interval; return _interval;
#endif #endif
#elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC)
@ -320,7 +356,7 @@ inline WebRtc_Word64 TickInterval::Microseconds() const
QueryPerformanceFrequency(&qpfreq); QueryPerformanceFrequency(&qpfreq);
return (_interval * 1000000) / qpfreq.QuadPart; return (_interval * 1000000) / qpfreq.QuadPart;
#else #else
// _interval is in ms // _interval is in ms
return _interval *1000LL; return _interval *1000LL;
#endif #endif
#elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC) #elif defined(WEBRTC_LINUX) || defined(WEBRTC_MAC)
@ -334,15 +370,16 @@ inline WebRtc_Word64 TickInterval::Microseconds() const
inline TickInterval& TickInterval::operator+=(const TickInterval& rhs) inline TickInterval& TickInterval::operator+=(const TickInterval& rhs)
{ {
_interval += rhs._interval; _interval += rhs._interval;
return *this; return *this;
} }
inline TickInterval& TickInterval::operator-=(const TickInterval& rhs) inline TickInterval& TickInterval::operator-=(const TickInterval& rhs)
{ {
_interval -= rhs._interval; _interval -= rhs._interval;
return *this; return *this;
} }
} // namespace webrtc } // namespace webrtc
#endif // WEBRTC_SYSTEM_WRAPPERS_INTERFACE_TICK_UTIL_H_ #endif // WEBRTC_SYSTEM_WRAPPERS_INTERFACE_TICK_UTIL_H_

View File

@ -40,6 +40,7 @@ LOCAL_SRC_FILES := \
event_posix.cc \ event_posix.cc \
sleep.cc \ sleep.cc \
thread_posix.cc \ thread_posix.cc \
tick_util.cc \
trace_posix.cc \ trace_posix.cc \
rw_lock_posix.cc rw_lock_posix.cc

View File

@ -91,14 +91,15 @@
'rw_lock_posix.h', 'rw_lock_posix.h',
'rw_lock_win.cc', 'rw_lock_win.cc',
'rw_lock_win.h', 'rw_lock_win.h',
'set_thread_name_win.h',
'sleep.cc', 'sleep.cc',
'sort.cc', 'sort.cc',
'tick_util.cc',
'thread.cc', 'thread.cc',
'thread_posix.cc', 'thread_posix.cc',
'thread_posix.h', 'thread_posix.h',
'thread_win.cc', 'thread_win.cc',
'thread_win.h', 'thread_win.h',
'set_thread_name_win.h',
'trace_impl.cc', 'trace_impl.cc',
'trace_impl.h', 'trace_impl.h',
'trace_impl_no_op.cc', 'trace_impl_no_op.cc',

View File

@ -0,0 +1,30 @@
/*
* Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
*
* Use of this source code is governed by a BSD-style license
* that can be found in the LICENSE file in the root of the source
* tree. An additional intellectual property rights grant can be found
* in the file PATENTS. All contributing project authors may
* be found in the AUTHORS file in the root of the source tree.
*/
#include "system_wrappers/interface/tick_util.h"
#include <cassert>
namespace webrtc {
bool TickTime::_use_fake_clock = false;
WebRtc_Word64 TickTime::_fake_ticks = 0;
void TickTime::UseFakeClock(WebRtc_Word64 start_millisecond) {
_use_fake_clock = true;
_fake_ticks = MillisecondsToTicks(start_millisecond);
}
void TickTime::AdvanceFakeClock(WebRtc_Word64 milliseconds) {
assert(_use_fake_clock);
_fake_ticks += MillisecondsToTicks(milliseconds);
}
} // namespace webrtc

View File

@ -454,7 +454,7 @@ void ViEAutoTest::ViECaptureExternalCaptureTest() {
while (frame_count < 120) { while (frame_count < 120) {
external_capture->IncomingFrame( external_capture->IncomingFrame(
video_frame, video_frame_length, capability, video_frame, video_frame_length, capability,
webrtc::TickTime::Now().MillisecondTimestamp()); webrtc::TickTime::MillisecondTimestamp());
AutoTestSleep(33); AutoTestSleep(33);
if (effect_filter.number_of_captured_frames_ > 2) { if (effect_filter.number_of_captured_frames_ > 2) {
@ -478,7 +478,7 @@ void ViEAutoTest::ViECaptureExternalCaptureTest() {
for (int frame = 0; frame < 30; ++frame) { for (int frame = 0; frame < 30; ++frame) {
external_capture->IncomingFrame( external_capture->IncomingFrame(
video_frame, video_frame_length, capability, video_frame, video_frame_length, capability,
webrtc::TickTime::Now().MillisecondTimestamp()); webrtc::TickTime::MillisecondTimestamp());
AutoTestSleep(33); AutoTestSleep(33);
} }
EXPECT_EQ(webrtc::Bright, observer.brightness_) << EXPECT_EQ(webrtc::Bright, observer.brightness_) <<
@ -491,7 +491,7 @@ void ViEAutoTest::ViECaptureExternalCaptureTest() {
for (int frame = 0; frame < 30; ++frame) { for (int frame = 0; frame < 30; ++frame) {
external_capture->IncomingFrame( external_capture->IncomingFrame(
video_frame, video_frame_length, capability, video_frame, video_frame_length, capability,
webrtc::TickTime::Now().MillisecondTimestamp()); webrtc::TickTime::MillisecondTimestamp());
AutoTestSleep(33); AutoTestSleep(33);
} }
EXPECT_EQ(webrtc::Dark, observer.brightness_) << EXPECT_EQ(webrtc::Dark, observer.brightness_) <<
@ -513,7 +513,7 @@ void ViEAutoTest::ViECaptureExternalCaptureTest() {
for (int frame = 0; frame < 10; ++frame) { for (int frame = 0; frame < 10; ++frame) {
external_capture->IncomingFrame( external_capture->IncomingFrame(
video_frame, video_frame_length, capability, video_frame, video_frame_length, capability,
webrtc::TickTime::Now().MillisecondTimestamp()); webrtc::TickTime::MillisecondTimestamp());
AutoTestSleep(33); AutoTestSleep(33);
} }
EXPECT_EQ(webrtc::AlarmCleared, observer.alarm_) << EXPECT_EQ(webrtc::AlarmCleared, observer.alarm_) <<

View File

@ -128,10 +128,9 @@ WebRtc_Word32 ViEReceiver::OnReceivedPayloadData(
const int packet_size = payload_size + rtp_header->header.paddingLength; const int packet_size = payload_size + rtp_header->header.paddingLength;
uint32_t compensated_timestamp = rtp_header->header.timestamp + uint32_t compensated_timestamp = rtp_header->header.timestamp +
rtp_header->extension.transmissionTimeOffset; rtp_header->extension.transmissionTimeOffset;
remote_bitrate_estimator_->IncomingPacket(rtp_header->header.ssrc, remote_bitrate_estimator_->IncomingPacket(
packet_size, rtp_header->header.ssrc, packet_size,
TickTime::MillisecondTimestamp(), TickTime::MillisecondTimestamp(), compensated_timestamp);
compensated_timestamp);
if (vcm_->IncomingPacket(payload_data, payload_size, *rtp_header) != 0) { if (vcm_->IncomingPacket(payload_data, payload_size, *rtp_header) != 0) {
// Check this... // Check this...
return -1; return -1;