1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
media / mojo / mojom / remoting.mojom [blame]
// Copyright 2016 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
module media.mojom;
import "media/mojo/mojom/media_types.mojom";
import "media/mojo/mojom/remoting_common.mojom";
import "ui/gfx/geometry/mojom/geometry.mojom";
interface RemoterFactory {
// Create a new Remoter associated with the given RemotingSource and bind it
// to the given interface receiver. The RemotingSource will be notified when
// the Remoter becomes available for use (or becomes unavailable).
Create(pending_remote<RemotingSource> source,
pending_receiver<Remoter> remoter);
};
// Interface used by the source to control when media bitstream data is read
// from a data pipe and then sent to the remote endpoint. There is one
// RemotingDataStreamSender per data pipe.
interface RemotingDataStreamSender {
// Enqueues a frame for transmission to the remote endpoint, with payload to
// be read from the data pipe. The callback will be invoked once the receiver
// is ready to read another frame, immediately following the writing of the
// sent |frame| to the underlying Openscreen sender.
//
// Only one such call may be in flight at a time.
SendFrame(media.mojom.DecoderBuffer frame) => ();
// Cancels the transmission of all in-flight data to the remote, up to and
// including the last SendFrame() call; and also discard any data chunks
// that were consumed from the data pipe for the next frame. This is used to
// optimize seeking, when it is known that any in-flight data is no longer
// needed by the remote. There is no guarantee as to how much of the in-flight
// data will actually reach the remote before the cancellation takes effect.
CancelInFlightData();
};
// Interface used by the source to start/stop remoting and send data to the
// sink.
interface Remoter {
// Starts a remoting session (once the sink has been reported to be available;
// see RemotingSource). Either RemotingSource.OnStarted() or OnStartFailed()
// will be called to indicate success or failure. Once OnStarted() has been
// invoked, the source may then make calls to SendMessageToSink() and expect
// messages from the remote via RemotingSource.OnMessageFromSink().
Start();
// Same as `Start()` except that Remoting will start without asking for users'
// permission.
StartWithPermissionAlreadyGranted();
// Starts remoting the media data streams. This is called after Start() to
// provide data pipes from which the audio/video bitstream data is consumed
// and then transported to the remote device. RemotingDataStreamSenders are
// used by the source to control when data should be consumed from the data
// pipes and sent. One or both pipes (and their corresponding
// RemotingDataStreamSender interface receivers) must be provided.
StartDataStreams(handle<data_pipe_consumer>? audio_pipe,
handle<data_pipe_consumer>? video_pipe,
pending_receiver<RemotingDataStreamSender>? audio_sender,
pending_receiver<RemotingDataStreamSender>? video_sender);
// Stops remoting media. Messages in both directions will be dropped after this
// point as well as any pending or in-transit media bitstream data.
Stop(RemotingStopReason reason);
// Sends |message| to the sink. |message| is a serialized protobuf from
// src/media/remoting/proto.
SendMessageToSink(array<uint8> message);
// Estimates the transmission capacity. Returns the result in
// bytes per second.
EstimateTransmissionCapacity() => (double rate);
};
// Interface used for sending notifications back to the local source's control
// logic, and to pass messages from the sink back to the local media pipeline.
interface RemotingSource {
// Pass the sink's metadata. It is up to the source's control logic to decide
// whether/when to start remoting.
OnSinkAvailable(RemotingSinkMetadata metadata);
// Notifies the source that the sink is no longer available for remoting. This
// may happen, for example, because the sink has been shut down, or because
// another source has started remoting.
OnSinkGone();
// One of these is called after the source attempts to start remoting. If
// OnStarted() is called, messages may begin flowing; and this will continue
// until OnStopped() is called. On the other hand, if OnStartFailed() is
// called, then no messages are being passed between source and sink and
// remoting is not taking place.
OnStarted();
OnStartFailed(RemotingStartFailReason reason);
// Passes a |message| from the sink back to the source. The |message| consists
// of a serialized protobuf from src/media/remoting/proto. This will only be
// called after OnStarted() and before OnStopped().
OnMessageFromSink(array<uint8> message);
// Notifies the source that remoting has terminated. This may or may not be in
// response to a Remoter.Stop() call, as other events (possibly external) may
// have caused remoting to end.
OnStopped(RemotingStopReason reason);
};
// Interface that is implemented by the host of RemotingSink and
// RemotingDataStreamReceiver. Remotee implementation would be implemented in
// the browser process in order to receive serialized RPC messages and frame
// data from the sender.
interface Remotee {
// Used by RemotingSink to notify Remotee that it is ready for remoting.
OnRemotingSinkReady(pending_remote<RemotingSink> sink);
// Used by the RemotingSink to send a serialized RPC message to sender side.
// |message| is a serialized protobuf from src/media/remoting/proto.
SendMessageToSource(array<uint8> message);
// Initialize the data pipe for RemotingDataStreamReceiver to allow Remotee to
// send frame data to it.
// Remoting media could be audio-only media, video-only media, or media has
// both audio and video. So, at least one of audio stream or video stream
// should be passed.
StartDataStreams(
pending_remote<RemotingDataStreamReceiver>? audio_stream,
pending_remote<RemotingDataStreamReceiver>? video_stream);
// Used by RemotingSink to notify Remotee that FlushUntil is happening in
// order to not send NACK for the frames that are ignored. The implementation
// should also forward the |{audio/video}_frame_count| to FlushUntil() of
// {audio|video} streams which are RemotingDataStreamReceiver implementations.
OnFlushUntil(uint32 audio_frame_count, uint32 video_frame_count);
// Used by RemotingSink to notify Remotee that VideoNaturalSizeChange is
// happening.
OnVideoNaturalSizeChange(gfx.mojom.Size size);
};
// Interface that is used to receive messages from the sender.
interface RemotingSink {
// Used by the Remotee to send a serialized RPC message to the sink.
// |message| is a serialized protobuf from src/media/remoting/proto.
OnMessageFromSource(array<uint8> message);
};
// Interface that is implemented by either an audio or a video demuxer stream at
// the receiver side to receive frame data. Passed to a Remotee which will send
// it frame data.
interface RemotingDataStreamReceiver {
// Used by the Remotee implementation to bind a data pipe to
// RemotingDataStreamReceiver.
InitializeDataPipe(handle<data_pipe_consumer> data_pipe);
// Used by the Remotee implementation to send frame data to
// RemotingDataStreamReceiver.
ReceiveFrame(uint32 frame_count, DecoderBuffer buffer);
// Used by the Remotee implementation to flush frames until the given frame
// count.
FlushUntil(uint32 frame_count);
};