xref: /aosp_15_r20/external/openscreen/cast/streaming/receiver_base.h (revision 3f982cf4871df8771c9d4abe6e9a6f8d829b2736)
1*3f982cf4SFabien Sanglard // Copyright 2021 The Chromium Authors. All rights reserved.
2*3f982cf4SFabien Sanglard // Use of this source code is governed by a BSD-style license that can be
3*3f982cf4SFabien Sanglard // found in the LICENSE file.
4*3f982cf4SFabien Sanglard 
5*3f982cf4SFabien Sanglard #ifndef CAST_STREAMING_RECEIVER_BASE_H_
6*3f982cf4SFabien Sanglard #define CAST_STREAMING_RECEIVER_BASE_H_
7*3f982cf4SFabien Sanglard 
8*3f982cf4SFabien Sanglard #include <chrono>
9*3f982cf4SFabien Sanglard 
10*3f982cf4SFabien Sanglard #include "absl/types/span.h"
11*3f982cf4SFabien Sanglard #include "cast/streaming/encoded_frame.h"
12*3f982cf4SFabien Sanglard #include "cast/streaming/session_config.h"
13*3f982cf4SFabien Sanglard #include "cast/streaming/ssrc.h"
14*3f982cf4SFabien Sanglard #include "platform/api/time.h"
15*3f982cf4SFabien Sanglard 
16*3f982cf4SFabien Sanglard namespace openscreen {
17*3f982cf4SFabien Sanglard namespace cast {
18*3f982cf4SFabien Sanglard 
19*3f982cf4SFabien Sanglard // The Cast Streaming Receiver, a peer corresponding to some Cast Streaming
20*3f982cf4SFabien Sanglard // Sender at the other end of a network link.
21*3f982cf4SFabien Sanglard //
22*3f982cf4SFabien Sanglard // Cast Streaming is a transport protocol which divides up the frames for one
23*3f982cf4SFabien Sanglard // media stream (e.g., audio or video) into multiple RTP packets containing an
24*3f982cf4SFabien Sanglard // encrypted payload. The Receiver is the peer responsible for collecting the
25*3f982cf4SFabien Sanglard // RTP packets, decrypting the payload, and re-assembling a frame that can be
26*3f982cf4SFabien Sanglard // passed to a decoder and played out.
27*3f982cf4SFabien Sanglard //
28*3f982cf4SFabien Sanglard // A Sender ↔ Receiver pair is used to transport each media stream. Typically,
29*3f982cf4SFabien Sanglard // there are two pairs in a normal system, one for the audio stream and one for
30*3f982cf4SFabien Sanglard // video stream. A local player is responsible for synchronizing the playout of
31*3f982cf4SFabien Sanglard // the frames of each stream to achieve lip-sync. See the discussion in
32*3f982cf4SFabien Sanglard // encoded_frame.h for how the |reference_time| and |rtp_timestamp| of the
33*3f982cf4SFabien Sanglard // EncodedFrames are used to achieve this.
34*3f982cf4SFabien Sanglard class ReceiverBase {
35*3f982cf4SFabien Sanglard  public:
36*3f982cf4SFabien Sanglard   class Consumer {
37*3f982cf4SFabien Sanglard    public:
38*3f982cf4SFabien Sanglard     virtual ~Consumer();
39*3f982cf4SFabien Sanglard 
40*3f982cf4SFabien Sanglard     // Called whenever one or more frames have become ready for consumption. The
41*3f982cf4SFabien Sanglard     // |next_frame_buffer_size| argument is identical to the result of calling
42*3f982cf4SFabien Sanglard     // AdvanceToNextFrame(), and so the Consumer only needs to prepare a buffer
43*3f982cf4SFabien Sanglard     // and call ConsumeNextFrame(). It may then call AdvanceToNextFrame() to
44*3f982cf4SFabien Sanglard     // check whether there are any more frames ready, but this is not mandatory.
45*3f982cf4SFabien Sanglard     // See usage example in class-level comments.
46*3f982cf4SFabien Sanglard     virtual void OnFramesReady(int next_frame_buffer_size) = 0;
47*3f982cf4SFabien Sanglard   };
48*3f982cf4SFabien Sanglard 
49*3f982cf4SFabien Sanglard   ReceiverBase();
50*3f982cf4SFabien Sanglard   virtual ~ReceiverBase();
51*3f982cf4SFabien Sanglard 
52*3f982cf4SFabien Sanglard   virtual const SessionConfig& config() const = 0;
53*3f982cf4SFabien Sanglard   virtual int rtp_timebase() const = 0;
54*3f982cf4SFabien Sanglard   virtual Ssrc ssrc() const = 0;
55*3f982cf4SFabien Sanglard 
56*3f982cf4SFabien Sanglard   // Set the Consumer receiving notifications when new frames are ready for
57*3f982cf4SFabien Sanglard   // consumption. Frames received before this method is called will remain in
58*3f982cf4SFabien Sanglard   // the queue indefinitely.
59*3f982cf4SFabien Sanglard   virtual void SetConsumer(Consumer* consumer) = 0;
60*3f982cf4SFabien Sanglard 
61*3f982cf4SFabien Sanglard   // Sets how much time the consumer will need to decode/buffer/render/etc., and
62*3f982cf4SFabien Sanglard   // otherwise fully process a frame for on-time playback. This information is
63*3f982cf4SFabien Sanglard   // used by the Receiver to decide whether to skip past frames that have
64*3f982cf4SFabien Sanglard   // arrived too late. This method can be called repeatedly to make adjustments
65*3f982cf4SFabien Sanglard   // based on changing environmental conditions.
66*3f982cf4SFabien Sanglard   //
67*3f982cf4SFabien Sanglard   // Default setting: kDefaultPlayerProcessingTime
68*3f982cf4SFabien Sanglard   virtual void SetPlayerProcessingTime(Clock::duration needed_time) = 0;
69*3f982cf4SFabien Sanglard 
70*3f982cf4SFabien Sanglard   // Propagates a "picture loss indicator" notification to the Sender,
71*3f982cf4SFabien Sanglard   // requesting a key frame so that decode/playout can recover. It is safe to
72*3f982cf4SFabien Sanglard   // call this redundantly. The Receiver will clear the picture loss condition
73*3f982cf4SFabien Sanglard   // automatically, once a key frame is received (i.e., before
74*3f982cf4SFabien Sanglard   // ConsumeNextFrame() is called to access it).
75*3f982cf4SFabien Sanglard   virtual void RequestKeyFrame() = 0;
76*3f982cf4SFabien Sanglard 
77*3f982cf4SFabien Sanglard   // Advances to the next frame ready for consumption. This may skip-over
78*3f982cf4SFabien Sanglard   // incomplete frames that will not play out on-time; but only if there are
79*3f982cf4SFabien Sanglard   // completed frames further down the queue that have no dependency
80*3f982cf4SFabien Sanglard   // relationship with them (e.g., key frames).
81*3f982cf4SFabien Sanglard   //
82*3f982cf4SFabien Sanglard   // This method returns kNoFramesReady if there is not currently a frame ready
83*3f982cf4SFabien Sanglard   // for consumption. The caller should wait for a Consumer::OnFramesReady()
84*3f982cf4SFabien Sanglard   // notification before trying again. Otherwise, the number of bytes of encoded
85*3f982cf4SFabien Sanglard   // data is returned, and the caller should use this to ensure the buffer it
86*3f982cf4SFabien Sanglard   // passes to ConsumeNextFrame() is large enough.
87*3f982cf4SFabien Sanglard   virtual int AdvanceToNextFrame() = 0;
88*3f982cf4SFabien Sanglard 
89*3f982cf4SFabien Sanglard   // Returns the next frame, both metadata and payload data. The Consumer calls
90*3f982cf4SFabien Sanglard   // this method after being notified via OnFramesReady(), and it can also call
91*3f982cf4SFabien Sanglard   // this whenever AdvanceToNextFrame() indicates another frame is ready.
92*3f982cf4SFabien Sanglard   // |buffer| must point to a sufficiently-sized buffer that will be populated
93*3f982cf4SFabien Sanglard   // with the frame's payload data. Upon return |frame->data| will be set to the
94*3f982cf4SFabien Sanglard   // portion of the buffer that was populated.
95*3f982cf4SFabien Sanglard   virtual EncodedFrame ConsumeNextFrame(absl::Span<uint8_t> buffer) = 0;
96*3f982cf4SFabien Sanglard 
97*3f982cf4SFabien Sanglard   // The default "player processing time" amount. See SetPlayerProcessingTime().
98*3f982cf4SFabien Sanglard   static constexpr std::chrono::milliseconds kDefaultPlayerProcessingTime{5};
99*3f982cf4SFabien Sanglard 
100*3f982cf4SFabien Sanglard   // Returned by AdvanceToNextFrame() when there are no frames currently ready
101*3f982cf4SFabien Sanglard   // for consumption.
102*3f982cf4SFabien Sanglard   static constexpr int kNoFramesReady = -1;
103*3f982cf4SFabien Sanglard };
104*3f982cf4SFabien Sanglard 
105*3f982cf4SFabien Sanglard }  // namespace cast
106*3f982cf4SFabien Sanglard }  // namespace openscreen
107*3f982cf4SFabien Sanglard 
108*3f982cf4SFabien Sanglard #endif  // CAST_STREAMING_RECEIVER_BASE_H_
109