1 /*
2  *  Copyright (c) 2019 The WebM project authors. All Rights Reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 #include "test/codec_factory.h"
11 #include "test/encode_test_driver.h"
12 #include "test/util.h"
13 #include "test/video_source.h"
14 #include "third_party/googletest/src/include/gtest/gtest.h"
15 
16 namespace {
17 
18 const int kVideoSourceWidth = 320;
19 const int kVideoSourceHeight = 240;
20 const int kFramesToEncode = 3;
21 
22 // A video source that exposes functions to set the timebase, framerate and
23 // starting pts.
24 class DummyTimebaseVideoSource : public ::libvpx_test::DummyVideoSource {
25  public:
26   // Parameters num and den set the timebase for the video source.
DummyTimebaseVideoSource(int num,int den)27   DummyTimebaseVideoSource(int num, int den)
28       : timebase_({ num, den }), framerate_numerator_(30),
29         framerate_denominator_(1), starting_pts_(0) {
30     SetSize(kVideoSourceWidth, kVideoSourceHeight);
31     set_limit(kFramesToEncode);
32   }
33 
SetFramerate(int numerator,int denominator)34   void SetFramerate(int numerator, int denominator) {
35     framerate_numerator_ = numerator;
36     framerate_denominator_ = denominator;
37   }
38 
39   // Returns one frames duration in timebase units as a double.
FrameDuration() const40   double FrameDuration() const {
41     return (static_cast<double>(timebase_.den) / timebase_.num) /
42            (static_cast<double>(framerate_numerator_) / framerate_denominator_);
43   }
44 
pts() const45   virtual vpx_codec_pts_t pts() const {
46     return static_cast<vpx_codec_pts_t>(frame_ * FrameDuration() +
47                                         starting_pts_ + 0.5);
48   }
49 
duration() const50   virtual unsigned long duration() const {
51     return static_cast<unsigned long>(FrameDuration() + 0.5);
52   }
53 
timebase() const54   virtual vpx_rational_t timebase() const { return timebase_; }
55 
set_starting_pts(int64_t starting_pts)56   void set_starting_pts(int64_t starting_pts) { starting_pts_ = starting_pts; }
57 
58  private:
59   vpx_rational_t timebase_;
60   int framerate_numerator_;
61   int framerate_denominator_;
62   int64_t starting_pts_;
63 };
64 
65 class TimestampTest
66     : public ::libvpx_test::EncoderTest,
67       public ::libvpx_test::CodecTestWithParam<libvpx_test::TestMode> {
68  protected:
TimestampTest()69   TimestampTest() : EncoderTest(GET_PARAM(0)) {}
~TimestampTest()70   virtual ~TimestampTest() {}
71 
SetUp()72   virtual void SetUp() {
73     InitializeConfig();
74     SetMode(GET_PARAM(1));
75   }
76 };
77 
78 // Tests encoding in millisecond timebase.
TEST_P(TimestampTest,EncodeFrames)79 TEST_P(TimestampTest, EncodeFrames) {
80   DummyTimebaseVideoSource video(1, 1000);
81   ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
82 }
83 
TEST_P(TimestampTest,TestMicrosecondTimebase)84 TEST_P(TimestampTest, TestMicrosecondTimebase) {
85   // Set the timebase to microseconds.
86   DummyTimebaseVideoSource video(1, 1000000);
87   video.set_limit(1);
88   ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
89 }
90 
TEST_P(TimestampTest,TestVpxRollover)91 TEST_P(TimestampTest, TestVpxRollover) {
92   DummyTimebaseVideoSource video(1, 1000);
93   video.set_starting_pts(922337170351ll);
94   ASSERT_NO_FATAL_FAILURE(RunLoop(&video));
95 }
96 
97 VP8_INSTANTIATE_TEST_CASE(TimestampTest,
98                           ::testing::Values(::libvpx_test::kTwoPassGood));
99 VP9_INSTANTIATE_TEST_CASE(TimestampTest,
100                           ::testing::Values(::libvpx_test::kTwoPassGood));
101 }  // namespace
102