mirror of
https://github.com/wjwwood/serial.git
synced 2026-01-22 19:54:57 +08:00
tests: Use elapsed time in timer tests (#232).
Compute actually elapsed time instead of assuming that usleep() sleeps for exactly the right time, which isn't guaranteed.
This commit is contained in:
parent
13ac389cbe
commit
2070f8ab68
@ -1,13 +1,31 @@
|
||||
#include <chrono>
|
||||
#include <sstream>
|
||||
#include <thread>
|
||||
|
||||
#include "gtest/gtest.h"
|
||||
#include "serial/impl/unix.h"
|
||||
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
using serial::MillisecondTimer;
|
||||
|
||||
namespace {
|
||||
|
||||
typedef std::chrono::high_resolution_clock Clock;
|
||||
|
||||
|
||||
template <typename T>
|
||||
std::chrono::milliseconds as_milliseconds(T duration)
|
||||
{
|
||||
return std::chrono::duration_cast<std::chrono::milliseconds>(duration);
|
||||
}
|
||||
|
||||
|
||||
struct test_timer {
|
||||
MillisecondTimer timer;
|
||||
std::chrono::time_point<Clock> start;
|
||||
test_timer(unsigned value): start(Clock::now()), timer(value) {}
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Do 100 trials of timing gaps between 0 and 19 milliseconds.
|
||||
* Expect accuracy within one millisecond.
|
||||
@ -15,48 +33,45 @@ namespace {
|
||||
TEST(timer_tests, short_intervals) {
|
||||
for (int trial = 0; trial < 100; trial++)
|
||||
{
|
||||
uint32_t ms = rand() % 20;
|
||||
MillisecondTimer mt(ms);
|
||||
usleep(1000 * ms);
|
||||
int32_t r = mt.remaining();
|
||||
|
||||
// 1ms slush, for the cost of calling usleep.
|
||||
EXPECT_NEAR(r+1, 0, 1);
|
||||
int ms = rand() % 20;
|
||||
auto t1 = Clock::now();
|
||||
MillisecondTimer mt(ms);
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(ms));
|
||||
int elapsed = as_milliseconds(Clock::now() - t1).count();
|
||||
EXPECT_NEAR(ms - elapsed, mt.remaining(), 1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
TEST(timer_tests, overlapping_long_intervals) {
|
||||
MillisecondTimer* timers[10];
|
||||
|
||||
// Experimentally determined. Corresponds to the extra time taken by the loops,
|
||||
// the big usleep, and the test infrastructure itself.
|
||||
const int slush_factor = 14;
|
||||
std::vector<test_timer> timers;
|
||||
|
||||
// Set up the timers to each time one second, 1ms apart.
|
||||
for (int t = 0; t < 10; t++)
|
||||
{
|
||||
timers[t] = new MillisecondTimer(1000);
|
||||
usleep(1000);
|
||||
// Set up the timers to each time one second, 1 ms apart.
|
||||
while (timers.size() < 10) {
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(1));
|
||||
struct test_timer timer(1000); // 1 s
|
||||
timers.push_back(timer);
|
||||
}
|
||||
|
||||
// Check in on them after 500ms.
|
||||
usleep(500000);
|
||||
for (int t = 0; t < 10; t++)
|
||||
{
|
||||
EXPECT_NEAR(timers[t]->remaining(), 500 - slush_factor + t, 5);
|
||||
// Check in on them after 500 ms.
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(500));
|
||||
for (auto& t: timers) {
|
||||
auto elapsed = as_milliseconds(Clock::now() - t.start).count();
|
||||
EXPECT_NEAR(1000 - elapsed, t.timer.remaining(), 1);
|
||||
}
|
||||
|
||||
// Check in on them again after another 500ms and free them.
|
||||
usleep(500000);
|
||||
for (int t = 0; t < 10; t++)
|
||||
{
|
||||
EXPECT_NEAR(timers[t]->remaining(), -slush_factor + t, 5);
|
||||
delete timers[t];
|
||||
// Check in on them again after another 500 ms.
|
||||
std::this_thread::sleep_for(std::chrono::milliseconds(500));
|
||||
for (auto& t: timers) {
|
||||
auto elapsed = as_milliseconds(Clock::now() - t.start).count();
|
||||
EXPECT_NEAR(1000 - elapsed, t.timer.remaining(), 1);
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
::testing::InitGoogleTest(&argc, argv);
|
||||
return RUN_ALL_TESTS();
|
||||
|
||||
@ -20,8 +20,6 @@ void loop()
|
||||
#include <string>
|
||||
#include "gtest/gtest.h"
|
||||
|
||||
#include <boost/bind.hpp>
|
||||
|
||||
// Use FRIEND_TEST... its not as nasty, thats what friends are for
|
||||
// // OMG this is so nasty...
|
||||
// #define private public
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user