live
MediaSession.hh
Go to the documentation of this file.
1/**********
2This library is free software; you can redistribute it and/or modify it under
3the terms of the GNU Lesser General Public License as published by the
4Free Software Foundation; either version 3 of the License, or (at your
5option) any later version. (See <http://www.gnu.org/copyleft/lesser.html>.)
6
7This library is distributed in the hope that it will be useful, but WITHOUT
8ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
9FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for
10more details.
11
12You should have received a copy of the GNU Lesser General Public License
13along with this library; if not, write to the Free Software Foundation, Inc.,
1451 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
15**********/
16// "liveMedia"
17// Copyright (c) 1996-2024 Live Networks, Inc. All rights reserved.
18// A data structure that represents a session that consists of
19// potentially multiple (audio and/or video) sub-sessions
20// (This data structure is used for media *receivers* - i.e., clients.
21// For media streamers, use "ServerMediaSession" instead.)
22// C++ header
23
24/* NOTE: To support receiving your own custom RTP payload format, you must first define a new
25 subclass of "MultiFramedRTPSource" (or "BasicUDPSource") that implements it.
26 Then define your own subclass of "MediaSession" and "MediaSubsession", as follows:
27 - In your subclass of "MediaSession" (named, for example, "myMediaSession"):
28 - Define and implement your own static member function
29 static myMediaSession* createNew(UsageEnvironment& env, char const* sdpDescription);
30 and call this - instead of "MediaSession::createNew()" - in your application,
31 when you create a new "MediaSession" object.
32 - Reimplement the "createNewMediaSubsession()" virtual function, as follows:
33 MediaSubsession* myMediaSession::createNewMediaSubsession() { return new myMediaSubsession(*this); }
34 - In your subclass of "MediaSubsession" (named, for example, "myMediaSubsession"):
35 - Reimplement the "createSourceObjects()" virtual function, perhaps similar to this:
36 Boolean myMediaSubsession::createSourceObjects(int useSpecialRTPoffset) {
37 if (strcmp(fCodecName, "X-MY-RTP-PAYLOAD-FORMAT") == 0) {
38 // This subsession uses our custom RTP payload format:
39 fReadSource = fRTPSource = myRTPPayloadFormatRTPSource::createNew( <parameters> );
40 return True;
41 } else {
42 // This subsession uses some other RTP payload format - perhaps one that we already implement:
43 return ::createSourceObjects(useSpecialRTPoffset);
44 }
45 }
46*/
47
48#ifndef _MEDIA_SESSION_HH
49#define _MEDIA_SESSION_HH
50
51#ifndef _RTCP_HH
52#include "RTCP.hh"
53#endif
54#ifndef _FRAMED_FILTER_HH
55#include "FramedFilter.hh"
56#endif
57#ifndef _SRTP_CRYPTOGRAPHIC_CONTEXT_HH
59#endif
60
61class MediaSubsession; // forward
62
63class MediaSession: public Medium {
64public:
66 char const* sdpDescription);
67
68 static Boolean lookupByName(UsageEnvironment& env, char const* sourceName,
69 MediaSession*& resultSession);
70
72
75 char const* CNAME() const { return fCNAME; }
76 struct sockaddr_storage const& sourceFilterAddr() const { return fSourceFilterAddr; }
77 float& scale() { return fScale; }
78 float& speed() { return fSpeed; }
79 char* mediaSessionType() const { return fMediaSessionType; }
80 char* sessionName() const { return fSessionName; }
81 char* sessionDescription() const { return fSessionDescription; }
82 char const* controlPath() const { return fControlPath; }
83
84 double& playStartTime() { return fMaxPlayStartTime; }
85 double& playEndTime() { return fMaxPlayEndTime; }
86 char* absStartTime() const;
87 char* absEndTime() const;
88 // Used only to set the local fields:
89 char*& _absStartTime() { return fAbsStartTime; }
90 char*& _absEndTime() { return fAbsEndTime; }
91
92 Boolean initiateByMediaType(char const* mimeType,
93 MediaSubsession*& resultSubsession,
94 int useSpecialRTPoffset = -1);
95 // Initiates the first subsession with the specified MIME type
96 // Returns the resulting subsession, or 'multi source' (not both)
97
100
101protected: // redefined virtual functions
102 virtual Boolean isMediaSession() const;
103
104protected:
106 // called only by createNew();
107 virtual ~MediaSession();
108
110
111 Boolean initializeWithSDP(char const* sdpDescription);
112 Boolean parseSDPLine(char const* input, char const*& nextLine);
113 Boolean parseSDPLine_s(char const* sdpLine);
114 Boolean parseSDPLine_i(char const* sdpLine);
115 Boolean parseSDPLine_c(char const* sdpLine);
116 Boolean parseSDPAttribute_type(char const* sdpLine);
117 Boolean parseSDPAttribute_control(char const* sdpLine);
118 Boolean parseSDPAttribute_range(char const* sdpLine);
121
122 static char* lookupPayloadFormat(unsigned char rtpPayloadType,
123 unsigned& rtpTimestampFrequency,
124 unsigned& numChannels);
125 static unsigned guessRTPTimestampFrequency(char const* mediumName,
126 char const* codecName);
127
128protected:
130 char* fCNAME; // used for RTCP
131
132 // Linkage fields:
135
136 // Fields set from a SDP description:
143 struct sockaddr_storage fSourceFilterAddr; // used for SSM
144 float fScale; // set from a RTSP "Scale:" header
145 float fSpeed;
146 char* fMediaSessionType; // holds a=type value
147 char* fSessionName; // holds s=<session name> value
148 char* fSessionDescription; // holds i=<session description> value
149 char* fControlPath; // holds optional a=control: string
150
151 // Optional key management and crypto state:
154};
155
156
158public:
161
162 MediaSubsession* next(); // NULL if none
163 void reset();
164
165private:
168};
169
170
172public:
174 MediaSession const& parentSession() const { return fParent; }
175
176 unsigned short clientPortNum() const { return fClientPortNum; }
177 unsigned char rtpPayloadFormat() const { return fRTPPayloadFormat; }
178 char const* savedSDPLines() const { return fSavedSDPLines; }
179 char const* mediumName() const { return fMediumName; }
180 char const* codecName() const { return fCodecName; }
181 char const* protocolName() const { return fProtocolName; }
182 char const* controlPath() const { return fControlPath; }
183
185
186 unsigned short videoWidth() const { return fVideoWidth; }
187 unsigned short videoHeight() const { return fVideoHeight; }
188 unsigned videoFPS() const { return fVideoFPS; }
189 unsigned numChannels() const { return fNumChannels; }
190 float& scale() { return fScale; }
191 float& speed() { return fSpeed; }
192
198 // This is the source that client sinks read from. It is usually
199 // (but not necessarily) the same as "rtpSource()"
200 void addFilter(FramedFilter* filter);
201 // Changes "readSource()" to "filter" (which must have just been created with "readSource()" as its input)
202
203 double playStartTime() const;
204 double playEndTime() const;
205 char* absStartTime() const;
206 char* absEndTime() const;
207 // Used only to set the local fields:
208 double& _playStartTime() { return fPlayStartTime; }
209 double& _playEndTime() { return fPlayEndTime; }
210 char*& _absStartTime() { return fAbsStartTime; }
211 char*& _absEndTime() { return fAbsEndTime; }
212
213 Boolean initiate(int useSpecialRTPoffset = -1);
214 // Creates a "RTPSource" for this subsession. (Has no effect if it's
215 // already been created.) Returns True iff this succeeds.
216 void deInitiate(); // Destroys any previously created RTPSource
218 // Sets the preferred client port number that any "RTPSource" for
219 // this subsession would use. (By default, the client port number
220 // is gotten from the original SDP description, or - if the SDP
221 // description does not specfy a client port number - an ephemeral
222 // (even) port number is chosen.) This routine must *not* be
223 // called after initiate().
224 void receiveRawMP3ADUs() { fReceiveRawMP3ADUs = True; } // optional hack for audio/MPA-ROBUST; must not be called after initiate()
225 void receiveRawJPEGFrames() { fReceiveRawJPEGFrames = True; } // optional hack for video/JPEG; must not be called after initiate()
227 char const* connectionEndpointName() const {
229 }
231 return fConnectionEndpointNameAddressFamily == AF_UNSPEC
234 }
235
236 // 'Bandwidth' parameter, set in the "b=" SDP line:
237 unsigned bandwidth() const { return fBandwidth; }
238
239 // General SDP attribute accessor functions:
240 char const* attrVal_str(char const* attrName) const;
241 // returns "" if attribute doesn't exist (and has no default value), or is not a string
242 char const* attrVal_strToLower(char const* attrName) const;
243 // returns "" if attribute doesn't exist (and has no default value), or is not a string
244 unsigned attrVal_int(char const* attrName) const;
245 // also returns 0 if attribute doesn't exist (and has no default value)
246 unsigned attrVal_unsigned(char const* attrName) const { return (unsigned)attrVal_int(attrName); }
247 Boolean attrVal_bool(char const* attrName) const { return attrVal_int(attrName) != 0; }
248
249 // Old, now-deprecated SDP attribute accessor functions, kept here for backwards-compatibility:
250 char const* fmtp_config() const;
251 char const* fmtp_configuration() const { return fmtp_config(); }
252 char const* fmtp_spropparametersets() const { return attrVal_str("sprop-parameter-sets"); }
253 char const* fmtp_spropvps() const { return attrVal_str("sprop-vps"); }
254 char const* fmtp_spropsps() const { return attrVal_str("sprop-sps"); }
255 char const* fmtp_sproppps() const { return attrVal_str("sprop-pps"); }
256
257 void getConnectionEndpointAddress(struct sockaddr_storage& addr) const;
258 // Converts "fConnectionEndpointName" to an address (or 0 if unknown)
259 void setDestinations(struct sockaddr_storage const& defaultDestAddress);
260 // Uses "fConnectionEndpointName" and "serverPortNum" to set
261 // the destination address and port of the RTP and RTCP objects.
262 // This is typically called by RTSP clients after doing "SETUP".
263
264 char const* sessionId() const { return fSessionId; }
265 void setSessionId(char const* sessionId);
266
267 // Public fields that external callers can use to keep state.
268 // (They are responsible for all storage management on these fields)
269 unsigned short serverPortNum; // in host byte order (used by RTSP)
270 unsigned char rtpChannelId, rtcpChannelId; // used by RTSP (for RTP/TCP)
271 MediaSink* sink; // callers can use this to keep track of who's playing us
272 void* miscPtr; // callers can use this for whatever they want
273
274 // Parameters set from a RTSP "RTP-Info:" header:
275 struct {
276 u_int16_t seqNum;
277 u_int32_t timestamp;
278 Boolean infoIsNew; // not part of the RTSP header; instead, set whenever this struct is filled in
280
281 double getNormalPlayTime(struct timeval const& presentationTime);
282 // Computes the stream's "Normal Play Time" (NPT) from the given "presentationTime".
283 // (For the definition of "Normal Play Time", see RFC 2326, section 3.6.)
284 // This function is useful only if the "rtpInfo" structure was previously filled in
285 // (e.g., by a "RTP-Info:" header in a RTSP response).
286 // Also, for this function to work properly, the RTP stream's presentation times must (eventually) be
287 // synchronized via RTCP.
288 // (Note: If this function returns a negative number, then the result should be ignored by the caller.)
289
292
293protected:
294 friend class MediaSession;
298
300 void setNext(MediaSubsession* next) { fNext = next; }
301
302 void setAttribute(char const* name, char const* value = NULL, Boolean valueIsHexadecimal = False);
303
304 Boolean parseSDPLine_c(char const* sdpLine);
305 Boolean parseSDPLine_b(char const* sdpLine);
306 Boolean parseSDPAttribute_rtpmap(char const* sdpLine);
307 Boolean parseSDPAttribute_rtcpmux(char const* sdpLine);
308 Boolean parseSDPAttribute_control(char const* sdpLine);
309 Boolean parseSDPAttribute_range(char const* sdpLine);
310 Boolean parseSDPAttribute_fmtp(char const* sdpLine);
315
316 virtual Boolean createSourceObjects(int useSpecialRTPoffset);
317 // create "fRTPSource" and "fReadSource" member objects, after we've been initialized via SDP
318
319protected:
320 // Linkage fields:
323
324 // Fields set from a SDP description:
325 char* fConnectionEndpointName; // may also be set by RTSP SETUP response
327 unsigned short fClientPortNum; // in host byte order
328 // This field is also set by initiate()
329 unsigned char fRTPPayloadFormat;
336 char* fControlPath; // holds optional a=control: string
337
338 // Optional key management and crypto state:
341
342 struct sockaddr_storage fSourceFilterAddr; // used for SSM
343 unsigned fBandwidth; // in kilobits-per-second, from b= line
344
349 unsigned short fVideoWidth, fVideoHeight;
350 // screen dimensions (set by an optional a=x-dimensions: <w>,<h> line)
351 unsigned fVideoFPS;
352 // frame rate (set by an optional "a=framerate: <fps>" or "a=x-framerate: <fps>" line)
353 unsigned fNumChannels;
354 // optionally set by "a=rtpmap:" lines for audio sessions. Default: 1
355 float fScale; // set from a RTSP "Scale:" header
356 float fSpeed;
357 double fNPT_PTS_Offset; // set by "getNormalPlayTime()"; add this to a PTS to get NPT
358 HashTable* fAttributeTable; // for "a=fmtp:" attributes. (Later an array by payload type #####)
359
360 // Fields set or used by initiate():
361 Groupsock* fRTPSocket; Groupsock* fRTCPSocket; // works even for unicast
365
366 // Other fields:
367 char* fSessionId; // used by RTSP
368};
369
370#endif
const Boolean False
Definition: Boolean.hh:28
const Boolean True
Definition: Boolean.hh:31
unsigned char Boolean
Definition: Boolean.hh:25
Boolean addressIsNull(sockaddr_storage const &address)
portNumBits portNum(struct sockaddr_storage const &address)
#define NULL
Boolean parseSDPAttribute_type(char const *sdpLine)
double fMaxPlayEndTime
Boolean parseSDPAttribute_control(char const *sdpLine)
Boolean parseSDPLine_i(char const *sdpLine)
char * absEndTime() const
char const * CNAME() const
Definition: MediaSession.hh:75
int connectionEndpointNameAddressFamily() const
Definition: MediaSession.hh:74
char * fConnectionEndpointName
char * connectionEndpointName() const
Definition: MediaSession.hh:73
Boolean initializeWithSDP(char const *sdpDescription)
Boolean hasSubsessions() const
Definition: MediaSession.hh:71
Boolean parseSDPAttribute_key_mgmt(char const *sdpLine)
char * fSessionDescription
Boolean parseSDPAttribute_range(char const *sdpLine)
MIKEYState * getMIKEYState() const
Definition: MediaSession.hh:98
char * mediaSessionType() const
Definition: MediaSession.hh:79
double & playEndTime()
Definition: MediaSession.hh:85
char * fMediaSessionType
MIKEYState * fMIKEYState
double fMaxPlayStartTime
static char * lookupPayloadFormat(unsigned char rtpPayloadType, unsigned &rtpTimestampFrequency, unsigned &numChannels)
SRTPCryptographicContext * getCrypto() const
Definition: MediaSession.hh:99
char * sessionDescription() const
Definition: MediaSession.hh:81
Boolean parseSDPAttribute_source_filter(char const *sdpLine)
virtual Boolean isMediaSession() const
char * sessionName() const
Definition: MediaSession.hh:80
MediaSubsession * fSubsessionsTail
float & speed()
Definition: MediaSession.hh:78
MediaSession(UsageEnvironment &env)
char * fAbsEndTime
struct sockaddr_storage const & sourceFilterAddr() const
Definition: MediaSession.hh:76
int fConnectionEndpointNameAddressFamily
float & scale()
Definition: MediaSession.hh:77
char * fSessionName
char * fAbsStartTime
char *& _absEndTime()
Definition: MediaSession.hh:90
virtual ~MediaSession()
Boolean parseSDPLine_s(char const *sdpLine)
char *& _absStartTime()
Definition: MediaSession.hh:89
char * fControlPath
static Boolean lookupByName(UsageEnvironment &env, char const *sourceName, MediaSession *&resultSession)
static MediaSession * createNew(UsageEnvironment &env, char const *sdpDescription)
Boolean initiateByMediaType(char const *mimeType, MediaSubsession *&resultSubsession, int useSpecialRTPoffset=-1)
char const * controlPath() const
Definition: MediaSession.hh:82
virtual MediaSubsession * createNewMediaSubsession()
Boolean parseSDPLine(char const *input, char const *&nextLine)
char * absStartTime() const
double & playStartTime()
Definition: MediaSession.hh:84
MediaSubsession * fSubsessionsHead
struct sockaddr_storage fSourceFilterAddr
static unsigned guessRTPTimestampFrequency(char const *mediumName, char const *codecName)
SRTPCryptographicContext * fCrypto
Boolean parseSDPLine_c(char const *sdpLine)
virtual ~MediaSubsessionIterator()
MediaSession const & fOurSession
MediaSubsession * fNextPtr
MediaSubsession * next()
MediaSubsessionIterator(MediaSession const &session)
MediaSession const & parentSession() const
Boolean parseSDPAttribute_control(char const *sdpLine)
unsigned attrVal_int(char const *attrName) const
void setSessionId(char const *sessionId)
void getConnectionEndpointAddress(struct sockaddr_storage &addr) const
unsigned attrVal_unsigned(char const *attrName) const
struct sockaddr_storage fSourceFilterAddr
Boolean fReceiveRawJPEGFrames
char const * savedSDPLines() const
MediaSession & fParent
double & _playStartTime()
unsigned short serverPortNum
char const * attrVal_strToLower(char const *attrName) const
RTCPInstance * rtcpInstance()
char const * fmtp_spropparametersets() const
double playStartTime() const
char const * fmtp_spropvps() const
char *& connectionEndpointName()
Boolean initiate(int useSpecialRTPoffset=-1)
Boolean attrVal_bool(char const *attrName) const
void setNext(MediaSubsession *next)
Boolean parseSDPLine_c(char const *sdpLine)
FramedSource * fReadSource
RTPSource * rtpSource()
RTCPInstance * fRTCPInstance
char const * controlPath() const
MediaSink * sink
unsigned char rtpPayloadFormat() const
virtual ~MediaSubsession()
char * fConnectionEndpointName
char const * fmtp_config() const
unsigned short fVideoWidth
Boolean isSSM() const
double fNPT_PTS_Offset
void receiveRawJPEGFrames()
Boolean rtcpIsMuxed() const
Boolean parseSDPAttribute_framerate(char const *sdpLine)
char const * protocolName() const
SRTPCryptographicContext * fCrypto
Boolean setClientPortNum(unsigned short portNum)
char const * attrVal_str(char const *attrName) const
char const * codecName() const
unsigned fRTPTimestampFrequency
double playEndTime() const
Boolean parseSDPLine_b(char const *sdpLine)
unsigned short fClientPortNum
Boolean fMultiplexRTCPWithRTP
unsigned numChannels() const
void setDestinations(struct sockaddr_storage const &defaultDestAddress)
unsigned bandwidth() const
MediaSubsession * fNext
unsigned short fVideoHeight
Boolean parseSDPAttribute_key_mgmt(char const *sdpLine)
MIKEYState * getMIKEYState() const
unsigned rtpTimestampFrequency() const
int fConnectionEndpointNameAddressFamily
char const * fmtp_sproppps() const
double & _playEndTime()
SRTPCryptographicContext * getCrypto() const
char const * mediumName() const
int connectionEndpointNameAddressFamily() const
Boolean parseSDPAttribute_rtpmap(char const *sdpLine)
struct MediaSubsession::@0 rtpInfo
Boolean parseSDPAttribute_range(char const *sdpLine)
unsigned fBandwidth
char const * fmtp_spropsps() const
MediaSubsession(MediaSession &parent)
double getNormalPlayTime(struct timeval const &presentationTime)
MIKEYState * fMIKEYState
char const * sessionId() const
MediaSession & parentSession()
Groupsock * fRTPSocket
unsigned char rtcpChannelId
unsigned short videoHeight() const
unsigned videoFPS() const
unsigned short clientPortNum() const
virtual Boolean createSourceObjects(int useSpecialRTPoffset)
void addFilter(FramedFilter *filter)
unsigned char fRTPPayloadFormat
char *& _absEndTime()
Boolean parseSDPAttribute_fmtp(char const *sdpLine)
unsigned char rtpChannelId
Boolean fReceiveRawMP3ADUs
char *& _absStartTime()
Boolean parseSDPAttribute_x_dimensions(char const *sdpLine)
char * absEndTime() const
FramedSource * readSource()
RTPSource * fRTPSource
HashTable * fAttributeTable
unsigned fNumChannels
void setAttribute(char const *name, char const *value=NULL, Boolean valueIsHexadecimal=False)
char const * fmtp_configuration() const
char const * connectionEndpointName() const
unsigned fVideoFPS
void receiveRawMP3ADUs()
UsageEnvironment & env()
u_int16_t seqNum
Groupsock * fRTCPSocket
char * absStartTime() const
unsigned short videoWidth() const
Boolean parseSDPAttribute_rtcpmux(char const *sdpLine)
u_int32_t timestamp
Boolean parseSDPAttribute_source_filter(char const *sdpLine)
Definition: Media.hh:50
UsageEnvironment & envir() const
Definition: Media.hh:59