Source code

Revision control

Other Tools

1
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2
/* vim: set sw=2 ts=8 et ft=cpp : */
3
/* This Source Code Form is subject to the terms of the Mozilla Public
4
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
5
* You can obtain one at http://mozilla.org/MPL/2.0/. */
6
7
#ifndef MEDIAENGINE_REMOTE_VIDEO_SOURCE_H_
8
#define MEDIAENGINE_REMOTE_VIDEO_SOURCE_H_
9
10
#include "prcvar.h"
11
#include "prthread.h"
12
#include "nsIThread.h"
13
#include "nsIRunnable.h"
14
15
#include "mozilla/Mutex.h"
16
#include "nsCOMPtr.h"
17
#include "nsThreadUtils.h"
18
#include "DOMMediaStream.h"
19
#include "nsDirectoryServiceDefs.h"
20
#include "nsComponentManagerUtils.h"
21
22
// Avoid warnings about redefinition of WARN_UNUSED_RESULT
23
#include "ipc/IPCMessageUtils.h"
24
#include "VideoUtils.h"
25
#include "MediaEngineSource.h"
26
#include "VideoSegment.h"
27
#include "AudioSegment.h"
28
#include "StreamTracks.h"
29
#include "MediaStreamGraph.h"
30
31
#include "MediaEngineWrapper.h"
32
#include "mozilla/dom/MediaStreamTrackBinding.h"
33
34
// Camera Access via IPC
35
#include "CamerasChild.h"
36
37
#include "NullTransport.h"
38
39
// WebRTC includes
40
#include "webrtc/common_video/include/i420_buffer_pool.h"
41
#include "webrtc/modules/video_capture/video_capture_defines.h"
42
43
namespace webrtc {
44
using CaptureCapability = VideoCaptureCapability;
45
}
46
47
namespace mozilla {
48
49
// Fitness distance is defined in
51
52
// The main difference of feasibility and fitness distance is that if the
53
// constraint is required ('max', or 'exact'), and the settings dictionary's
54
// value for the constraint does not satisfy the constraint, the fitness
55
// distance is positive infinity. Given a continuous space of settings
56
// dictionaries comprising all discrete combinations of dimension and frame-rate
57
// related properties, the feasibility distance is still in keeping with the
58
// constraints algorithm.
59
enum DistanceCalculation { kFitness, kFeasibility };
60
61
/**
62
* The WebRTC implementation of the MediaEngine interface.
63
*/
64
class MediaEngineRemoteVideoSource : public MediaEngineSource,
65
public camera::FrameRelay {
66
~MediaEngineRemoteVideoSource();
67
68
struct CapabilityCandidate {
69
explicit CapabilityCandidate(webrtc::CaptureCapability aCapability,
70
uint32_t aDistance = 0)
71
: mCapability(aCapability), mDistance(aDistance) {}
72
73
const webrtc::CaptureCapability mCapability;
74
uint32_t mDistance;
75
};
76
77
class CapabilityComparator {
78
public:
79
bool Equals(const CapabilityCandidate& aCandidate,
80
const webrtc::CaptureCapability& aCapability) const {
81
return aCandidate.mCapability == aCapability;
82
}
83
};
84
85
bool ChooseCapability(const NormalizedConstraints& aConstraints,
86
const MediaEnginePrefs& aPrefs,
87
const nsString& aDeviceId,
88
webrtc::CaptureCapability& aCapability,
89
const DistanceCalculation aCalculate);
90
91
uint32_t GetDistance(const webrtc::CaptureCapability& aCandidate,
92
const NormalizedConstraintSet& aConstraints,
93
const nsString& aDeviceId,
94
const DistanceCalculation aCalculate) const;
95
96
uint32_t GetFitnessDistance(const webrtc::CaptureCapability& aCandidate,
97
const NormalizedConstraintSet& aConstraints,
98
const nsString& aDeviceId) const;
99
100
uint32_t GetFeasibilityDistance(const webrtc::CaptureCapability& aCandidate,
101
const NormalizedConstraintSet& aConstraints,
102
const nsString& aDeviceId) const;
103
104
static void TrimLessFitCandidates(nsTArray<CapabilityCandidate>& aSet);
105
106
uint32_t GetBestFitnessDistance(
107
const nsTArray<const NormalizedConstraintSet*>& aConstraintSets,
108
const nsString& aDeviceId) const override;
109
110
public:
111
MediaEngineRemoteVideoSource(int aIndex, camera::CaptureEngine aCapEngine,
112
bool aScary);
113
114
// ExternalRenderer
115
int DeliverFrame(uint8_t* aBuffer,
116
const camera::VideoFrameProperties& aProps) override;
117
118
// MediaEngineSource
119
dom::MediaSourceEnum GetMediaSource() const override;
120
nsresult Allocate(const dom::MediaTrackConstraints& aConstraints,
121
const MediaEnginePrefs& aPrefs, const nsString& aDeviceId,
122
const ipc::PrincipalInfo& aPrincipalInfo,
123
const char** aOutBadConstraint) override;
124
nsresult Deallocate() override;
125
void SetTrack(const RefPtr<SourceMediaStream>& aStream, TrackID aTrackID,
126
const PrincipalHandle& aPrincipal) override;
127
nsresult Start() override;
128
nsresult Reconfigure(const dom::MediaTrackConstraints& aConstraints,
129
const MediaEnginePrefs& aPrefs,
130
const nsString& aDeviceId,
131
const char** aOutBadConstraint) override;
132
nsresult FocusOnSelectedSource() override;
133
nsresult Stop() override;
134
135
void GetSettings(dom::MediaTrackSettings& aOutSettings) const override;
136
137
void Refresh(int aIndex);
138
139
void Shutdown() override;
140
141
nsString GetName() const override;
142
void SetName(nsString aName);
143
144
nsCString GetUUID() const override;
145
void SetUUID(const char* aUUID);
146
147
nsString GetGroupId() const override;
148
void SetGroupId(nsString aGroupId);
149
150
bool GetScary() const override { return mScary; }
151
152
RefPtr<GenericNonExclusivePromise> GetFirstFramePromise() const override {
153
return mFirstFramePromise;
154
}
155
156
private:
157
// Initialize the needed Video engine interfaces.
158
void Init();
159
160
/**
161
* Returns the number of capabilities for the underlying device.
162
*
163
* Guaranteed to return at least one capability.
164
*/
165
size_t NumCapabilities() const;
166
167
/**
168
* Returns the capability with index `aIndex` for our assigned device.
169
*
170
* It is an error to call this with `aIndex >= NumCapabilities()`.
171
*/
172
webrtc::CaptureCapability GetCapability(size_t aIndex) const;
173
174
int mCaptureIndex;
175
const camera::CaptureEngine mCapEngine; // source of media (cam, screen etc)
176
const bool mScary;
177
178
// mMutex protects certain members on 3 threads:
179
// MediaManager, Cameras IPC and MediaStreamGraph.
180
Mutex mMutex;
181
182
// Current state of this source.
183
// Set under mMutex on the owning thread. Accessed under one of the two.
184
MediaEngineSourceState mState = kReleased;
185
186
// The source stream that we feed video data to.
187
// Set under mMutex on the owning thread. Accessed under one of the two.
188
RefPtr<SourceMediaStream> mStream;
189
190
// The TrackID in mStream that we feed video data to.
191
// Set under mMutex on the owning thread. Accessed under one of the two.
192
TrackID mTrackID = TRACK_NONE;
193
194
// The PrincipalHandle that gets attached to the frames we feed to mStream.
195
// Set under mMutex on the owning thread. Accessed under one of the two.
196
PrincipalHandle mPrincipal = PRINCIPAL_HANDLE_NONE;
197
198
// Set in Start() and Deallocate() on the owning thread.
199
// Accessed in DeliverFrame() on the camera IPC thread, guaranteed to happen
200
// after Start() and before the end of Stop().
201
RefPtr<layers::ImageContainer> mImageContainer;
202
203
// A buffer pool used to manage the temporary buffer used when rescaling
204
// incoming images. Cameras IPC thread only.
205
webrtc::I420BufferPool mRescalingBufferPool;
206
207
// The intrinsic size of the latest captured image, so we can feed black
208
// images of the same size while stopped.
209
// Set under mMutex on the Cameras IPC thread. Accessed under one of the two.
210
gfx::IntSize mImageSize = gfx::IntSize(0, 0);
211
212
struct AtomicBool {
213
Atomic<bool> mValue;
214
};
215
216
// True when resolution settings have been updated from a real frame's
217
// resolution. Threadsafe.
218
// TODO: This can be removed in bug 1453269.
219
const RefPtr<media::Refcountable<AtomicBool>> mSettingsUpdatedByFrame;
220
221
// The current settings of this source.
222
// Note that these may be different from the settings of the underlying device
223
// since we scale frames to avoid fingerprinting.
224
// Members are main thread only.
225
const RefPtr<media::Refcountable<dom::MediaTrackSettings>> mSettings;
226
MozPromiseHolder<GenericNonExclusivePromise> mFirstFramePromiseHolder;
227
RefPtr<GenericNonExclusivePromise> mFirstFramePromise;
228
229
// The capability currently chosen by constraints of the user of this source.
230
// Set under mMutex on the owning thread. Accessed under one of the two.
231
webrtc::CaptureCapability mCapability;
232
233
/**
234
* Capabilities that we choose between when applying constraints.
235
*
236
* This is mutable so that the const method NumCapabilities() can reset it.
237
* Owning thread only.
238
*/
239
mutable nsTArray<webrtc::CaptureCapability> mHardcodedCapabilities;
240
241
nsString mDeviceName;
242
nsCString mUniqueId;
243
nsString mGroupId;
244
Maybe<nsString> mFacingMode;
245
246
// Whether init has successfully completed.
247
// Set in Init(), reset in Shutdown().
248
// Owning thread only.
249
bool mInitDone = false;
250
};
251
252
} // namespace mozilla
253
254
#endif /* MEDIAENGINE_REMOTE_VIDEO_SOURCE_H_ */