Mercurial > libavformat.hg
annotate rtsp.c @ 5644:95e016b6158c libavformat
Don't forget to set known audio parameters (samplerate, etc.) if the codec is
not supported in FFmpeg. This will cause crashes later because the samplerate
is used to initialize the timebase.
author | rbultje |
---|---|
date | Wed, 10 Feb 2010 18:30:55 +0000 |
parents | dca2836e09b8 |
children | ebf397240c91 |
rev | line source |
---|---|
0 | 1 /* |
2 * RTSP/SDP client | |
4251
77e0c7511d41
cosmetics: Remove pointless period after copyright statement non-sentences.
diego
parents:
4206
diff
changeset
|
3 * Copyright (c) 2002 Fabrice Bellard |
0 | 4 * |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
5 * This file is part of FFmpeg. |
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
6 * |
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
7 * FFmpeg is free software; you can redistribute it and/or |
0 | 8 * modify it under the terms of the GNU Lesser General Public |
9 * License as published by the Free Software Foundation; either | |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
10 * version 2.1 of the License, or (at your option) any later version. |
0 | 11 * |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
12 * FFmpeg is distributed in the hope that it will be useful, |
0 | 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
15 * Lesser General Public License for more details. | |
16 * | |
17 * You should have received a copy of the GNU Lesser General Public | |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1169
diff
changeset
|
18 * License along with FFmpeg; if not, write to the Free Software |
896
edbe5c3717f9
Update licensing information: The FSF changed postal address.
diego
parents:
887
diff
changeset
|
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
0 | 20 */ |
3286 | 21 |
3722
68749aaea50f
ensure we get explicit definition of various _XOPEN_SOURCE functions we use
aurel
parents:
3714
diff
changeset
|
22 /* needed by inet_aton() */ |
68749aaea50f
ensure we get explicit definition of various _XOPEN_SOURCE functions we use
aurel
parents:
3714
diff
changeset
|
23 #define _SVID_SOURCE |
68749aaea50f
ensure we get explicit definition of various _XOPEN_SOURCE functions we use
aurel
parents:
3714
diff
changeset
|
24 |
5220
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
25 #include "libavutil/base64.h" |
3286 | 26 #include "libavutil/avstring.h" |
4201
7d2f3f1b68d8
Fix build: Add intreadwrite.h and bswap.h #includes where necessary.
diego
parents:
4187
diff
changeset
|
27 #include "libavutil/intreadwrite.h" |
0 | 28 #include "avformat.h" |
29 | |
1808
572ce77d7333
Fix compilation on Mac OS X, patch by Marc Hoffman, mmh pleasantst com.
diego
parents:
1754
diff
changeset
|
30 #include <sys/time.h> |
4206 | 31 #if HAVE_SYS_SELECT_H |
3936
6154f62ef652
include sys/select.h instead of unistd.h to get select,
bcoudurier
parents:
3924
diff
changeset
|
32 #include <sys/select.h> |
3941
53c5b89b8dff
only include sys/select.h if present, fix mingw compilation
bcoudurier
parents:
3936
diff
changeset
|
33 #endif |
3714 | 34 #include <strings.h> |
1754 | 35 #include "network.h" |
2681
6037eb4919fb
Remove the inclusion of rtsp.h and rtp.h from avformat.h, and
lucabe
parents:
2408
diff
changeset
|
36 #include "rtsp.h" |
0 | 37 |
4388 | 38 #include "rtpdec.h" |
3876
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
39 #include "rdt.h" |
4744
51899c07a4f1
Add RTP/ASF header parsing, which is part of the SDP of these streams. See
rbultje
parents:
4667
diff
changeset
|
40 #include "rtp_asf.h" |
4875
13a2a1a475d5
Add a Vorbis payload parser. Implemented by Colin McQuillan as a GSoC
rbultje
parents:
4874
diff
changeset
|
41 #include "rtp_vorbis.h" |
1419 | 42 |
0 | 43 //#define DEBUG |
172 | 44 //#define DEBUG_RTP_TCP |
0 | 45 |
2884 | 46 #if LIBAVFORMAT_VERSION_INT < (53 << 16) |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
47 int rtsp_default_protocols = (1 << RTSP_LOWER_TRANSPORT_UDP); |
2884 | 48 #endif |
0 | 49 |
4773
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
50 #define SPACE_CHARS " \t\r\n" |
4789
c18ea19a9771
strchr(string, '\0') returns non-NULL, and is thus not suited for use in
rbultje
parents:
4779
diff
changeset
|
51 /* we use memchr() instead of strchr() here because strchr() will return |
c18ea19a9771
strchr(string, '\0') returns non-NULL, and is thus not suited for use in
rbultje
parents:
4779
diff
changeset
|
52 * the terminating '\0' of SPACE_CHARS instead of NULL if c is '\0'. */ |
c18ea19a9771
strchr(string, '\0') returns non-NULL, and is thus not suited for use in
rbultje
parents:
4779
diff
changeset
|
53 #define redir_isspace(c) memchr(SPACE_CHARS, c, 4) |
0 | 54 static void skip_spaces(const char **pp) |
55 { | |
56 const char *p; | |
57 p = *pp; | |
58 while (redir_isspace(*p)) | |
59 p++; | |
60 *pp = p; | |
61 } | |
62 | |
4773
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
63 static void get_word_until_chars(char *buf, int buf_size, |
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
64 const char *sep, const char **pp) |
0 | 65 { |
66 const char *p; | |
67 char *q; | |
68 | |
69 p = *pp; | |
70 skip_spaces(&p); | |
71 q = buf; | |
72 while (!strchr(sep, *p) && *p != '\0') { | |
73 if ((q - buf) < buf_size - 1) | |
74 *q++ = *p; | |
75 p++; | |
76 } | |
77 if (buf_size > 0) | |
78 *q = '\0'; | |
79 *pp = p; | |
80 } | |
81 | |
4773
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
82 static void get_word_sep(char *buf, int buf_size, const char *sep, |
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
83 const char **pp) |
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
84 { |
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
85 if (**pp == '/') (*pp)++; |
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
86 get_word_until_chars(buf, buf_size, sep, pp); |
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
87 } |
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
88 |
0 | 89 static void get_word(char *buf, int buf_size, const char **pp) |
90 { | |
4773
1c9751d3065c
Merge functional code from get_word() and get_word_sep() into a single
rbultje
parents:
4772
diff
changeset
|
91 get_word_until_chars(buf, buf_size, SPACE_CHARS, pp); |
0 | 92 } |
93 | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
94 /* parse the rtpmap description: <codec_name>/<clock_rate>[/<other params>] */ |
5503
4ec7bcff8719
Add correct log context to av_log() calls in parse_rtpmap().
rbultje
parents:
5502
diff
changeset
|
95 static int sdp_parse_rtpmap(AVFormatContext *s, |
4ec7bcff8719
Add correct log context to av_log() calls in parse_rtpmap().
rbultje
parents:
5502
diff
changeset
|
96 AVCodecContext *codec, RTSPStream *rtsp_st, |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
97 int payload_type, const char *p) |
0 | 98 { |
99 char buf[256]; | |
774 | 100 int i; |
101 AVCodec *c; | |
1124
d3aff2c607f9
Add const to (mostly) char* and make some functions static, which aren't used
diego
parents:
1003
diff
changeset
|
102 const char *c_name; |
0 | 103 |
774 | 104 /* Loop into AVRtpDynamicPayloadTypes[] and AVRtpPayloadTypes[] and |
5529
0a67dbb939a0
Fix issue1658 (trailing space in rtpmap descriptor).
rbultje
parents:
5503
diff
changeset
|
105 * see if we can handle this kind of payload. |
0a67dbb939a0
Fix issue1658 (trailing space in rtpmap descriptor).
rbultje
parents:
5503
diff
changeset
|
106 * The space should normally not be there but some Real streams or |
0a67dbb939a0
Fix issue1658 (trailing space in rtpmap descriptor).
rbultje
parents:
5503
diff
changeset
|
107 * particular servers ("RealServer Version 6.1.3.970", see issue 1658) |
0a67dbb939a0
Fix issue1658 (trailing space in rtpmap descriptor).
rbultje
parents:
5503
diff
changeset
|
108 * have a trailing space. */ |
0a67dbb939a0
Fix issue1658 (trailing space in rtpmap descriptor).
rbultje
parents:
5503
diff
changeset
|
109 get_word_sep(buf, sizeof(buf), "/ ", &p); |
774 | 110 if (payload_type >= RTP_PT_PRIVATE) { |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
111 RTPDynamicProtocolHandler *handler; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
112 for (handler = RTPFirstDynamicPayloadHandler; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
113 handler; handler = handler->next) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
114 if (!strcasecmp(buf, handler->enc_name) && |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
115 codec->codec_type == handler->codec_type) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
116 codec->codec_id = handler->codec_id; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
117 rtsp_st->dynamic_handler = handler; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
118 if (handler->open) |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
119 rtsp_st->dynamic_protocol_context = handler->open(); |
774 | 120 break; |
121 } | |
1419 | 122 } |
774 | 123 } else { |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
124 /* We are in a standard case |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
125 * (from http://www.iana.org/assignments/rtp-parameters). */ |
774 | 126 /* search into AVRtpPayloadTypes[] */ |
2759
b252e318023a
Remove the "AVRtpPayloadTypes[i].pt == i" assumption from RTP and RTSP
lucabe
parents:
2711
diff
changeset
|
127 codec->codec_id = ff_rtp_codec_id(buf, codec->codec_type); |
774 | 128 } |
129 | |
130 c = avcodec_find_decoder(codec->codec_id); | |
131 if (c && c->name) | |
1124
d3aff2c607f9
Add const to (mostly) char* and make some functions static, which aren't used
diego
parents:
1003
diff
changeset
|
132 c_name = c->name; |
774 | 133 else |
5644
95e016b6158c
Don't forget to set known audio parameters (samplerate, etc.) if the codec is
rbultje
parents:
5589
diff
changeset
|
134 c_name = "(null)"; |
774 | 135 |
136 get_word_sep(buf, sizeof(buf), "/", &p); | |
137 i = atoi(buf); | |
138 switch (codec->codec_type) { | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
139 case CODEC_TYPE_AUDIO: |
5503
4ec7bcff8719
Add correct log context to av_log() calls in parse_rtpmap().
rbultje
parents:
5502
diff
changeset
|
140 av_log(s, AV_LOG_DEBUG, "audio codec set to: %s\n", c_name); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
141 codec->sample_rate = RTSP_DEFAULT_AUDIO_SAMPLERATE; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
142 codec->channels = RTSP_DEFAULT_NB_AUDIO_CHANNELS; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
143 if (i > 0) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
144 codec->sample_rate = i; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
145 get_word_sep(buf, sizeof(buf), "/", &p); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
146 i = atoi(buf); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
147 if (i > 0) |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
148 codec->channels = i; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
149 // TODO: there is a bug here; if it is a mono stream, and |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
150 // less than 22000Hz, faad upconverts to stereo and twice |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
151 // the frequency. No problem, but the sample rate is being |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
152 // set here by the sdp line. Patch on its way. (rdm) |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
153 } |
5503
4ec7bcff8719
Add correct log context to av_log() calls in parse_rtpmap().
rbultje
parents:
5502
diff
changeset
|
154 av_log(s, AV_LOG_DEBUG, "audio samplerate set to: %i\n", |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
155 codec->sample_rate); |
5503
4ec7bcff8719
Add correct log context to av_log() calls in parse_rtpmap().
rbultje
parents:
5502
diff
changeset
|
156 av_log(s, AV_LOG_DEBUG, "audio channels set to: %i\n", |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
157 codec->channels); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
158 break; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
159 case CODEC_TYPE_VIDEO: |
5503
4ec7bcff8719
Add correct log context to av_log() calls in parse_rtpmap().
rbultje
parents:
5502
diff
changeset
|
160 av_log(s, AV_LOG_DEBUG, "video codec set to: %s\n", c_name); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
161 break; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
162 default: |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
163 break; |
774 | 164 } |
0 | 165 return 0; |
166 } | |
167 | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
168 /* return the length and optionally the data */ |
0 | 169 static int hex_to_data(uint8_t *data, const char *p) |
170 { | |
171 int c, len, v; | |
172 | |
173 len = 0; | |
174 v = 1; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
175 for (;;) { |
0 | 176 skip_spaces(&p); |
4776
894e353aaeca
Fix silly bug in hex_to_data() where it compares a string pointer for whether
rbultje
parents:
4775
diff
changeset
|
177 if (*p == '\0') |
0 | 178 break; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
179 c = toupper((unsigned char) *p++); |
0 | 180 if (c >= '0' && c <= '9') |
181 c = c - '0'; | |
182 else if (c >= 'A' && c <= 'F') | |
183 c = c - 'A' + 10; | |
184 else | |
185 break; | |
186 v = (v << 4) | c; | |
187 if (v & 0x100) { | |
188 if (data) | |
189 data[len] = v; | |
190 len++; | |
191 v = 1; | |
192 } | |
193 } | |
194 return len; | |
195 } | |
196 | |
4875
13a2a1a475d5
Add a Vorbis payload parser. Implemented by Colin McQuillan as a GSoC
rbultje
parents:
4874
diff
changeset
|
197 static void sdp_parse_fmtp_config(AVCodecContext * codec, void *ctx, |
13a2a1a475d5
Add a Vorbis payload parser. Implemented by Colin McQuillan as a GSoC
rbultje
parents:
4874
diff
changeset
|
198 char *attr, char *value) |
774 | 199 { |
200 switch (codec->codec_id) { | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
201 case CODEC_ID_MPEG4: |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
202 case CODEC_ID_AAC: |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
203 if (!strcmp(attr, "config")) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
204 /* decode the hexa encoded parameter */ |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
205 int len = hex_to_data(NULL, value); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
206 if (codec->extradata) |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
207 av_free(codec->extradata); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
208 codec->extradata = av_mallocz(len + FF_INPUT_BUFFER_PADDING_SIZE); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
209 if (!codec->extradata) |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
210 return; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
211 codec->extradata_size = len; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
212 hex_to_data(codec->extradata, value); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
213 } |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
214 break; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
215 case CODEC_ID_VORBIS: |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
216 ff_vorbis_parse_fmtp_config(codec, ctx, attr, value); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
217 break; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
218 default: |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
219 break; |
774 | 220 } |
221 return; | |
222 } | |
223 | |
4088 | 224 typedef struct { |
1124
d3aff2c607f9
Add const to (mostly) char* and make some functions static, which aren't used
diego
parents:
1003
diff
changeset
|
225 const char *str; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
226 uint16_t type; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
227 uint32_t offset; |
4088 | 228 } AttrNameMap; |
774 | 229 |
230 /* All known fmtp parmeters and the corresping RTPAttrTypeEnum */ | |
231 #define ATTR_NAME_TYPE_INT 0 | |
232 #define ATTR_NAME_TYPE_STR 1 | |
4088 | 233 static const AttrNameMap attr_names[]= |
774 | 234 { |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
235 { "SizeLength", ATTR_NAME_TYPE_INT, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
236 offsetof(RTPPayloadData, sizelength) }, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
237 { "IndexLength", ATTR_NAME_TYPE_INT, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
238 offsetof(RTPPayloadData, indexlength) }, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
239 { "IndexDeltaLength", ATTR_NAME_TYPE_INT, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
240 offsetof(RTPPayloadData, indexdeltalength) }, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
241 { "profile-level-id", ATTR_NAME_TYPE_INT, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
242 offsetof(RTPPayloadData, profile_level_id) }, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
243 { "StreamType", ATTR_NAME_TYPE_INT, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
244 offsetof(RTPPayloadData, streamtype) }, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
245 { "mode", ATTR_NAME_TYPE_STR, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
246 offsetof(RTPPayloadData, mode) }, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
247 { NULL, -1, -1 }, |
774 | 248 }; |
249 | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
250 /* parse the attribute line from the fmtp a line of an sdp resonse. This |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
251 * is broken out as a function because it is used in rtp_h264.c, which is |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
252 * forthcoming. */ |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
253 int rtsp_next_attr_and_value(const char **p, char *attr, int attr_size, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
254 char *value, int value_size) |
1431
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
255 { |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
256 skip_spaces(p); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
257 if (**p) { |
1431
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
258 get_word_sep(attr, attr_size, "=", p); |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
259 if (**p == '=') |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
260 (*p)++; |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
261 get_word_sep(value, value_size, ";", p); |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
262 if (**p == ';') |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
263 (*p)++; |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
264 return 1; |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
265 } |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
266 return 0; |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
267 } |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
268 |
774 | 269 /* parse a SDP line and save stream attributes */ |
270 static void sdp_parse_fmtp(AVStream *st, const char *p) | |
0 | 271 { |
272 char attr[256]; | |
4874
5370b0c1653c
Increase the SDP buffer size (again!) and also increase the temporary
rbultje
parents:
4789
diff
changeset
|
273 /* Vorbis setup headers can be up to 12KB and are sent base64 |
5370b0c1653c
Increase the SDP buffer size (again!) and also increase the temporary
rbultje
parents:
4789
diff
changeset
|
274 * encoded, giving a 12KB * (4/3) = 16KB FMTP line. */ |
5370b0c1653c
Increase the SDP buffer size (again!) and also increase the temporary
rbultje
parents:
4789
diff
changeset
|
275 char value[16384]; |
774 | 276 int i; |
277 RTSPStream *rtsp_st = st->priv_data; | |
820
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
774
diff
changeset
|
278 AVCodecContext *codec = st->codec; |
4101
af2c0aef892b
Rename rtp_payload_data_t to avoid clashes with the POSIX namespace
lucabe
parents:
4088
diff
changeset
|
279 RTPPayloadData *rtp_payload_data = &rtsp_st->rtp_payload_data; |
0 | 280 |
281 /* loop on each attribute */ | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
282 while (rtsp_next_attr_and_value(&p, attr, sizeof(attr), |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
283 value, sizeof(value))) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
284 /* grab the codec extra_data from the config parameter of the fmtp |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
285 * line */ |
4875
13a2a1a475d5
Add a Vorbis payload parser. Implemented by Colin McQuillan as a GSoC
rbultje
parents:
4874
diff
changeset
|
286 sdp_parse_fmtp_config(codec, rtsp_st->dynamic_protocol_context, |
13a2a1a475d5
Add a Vorbis payload parser. Implemented by Colin McQuillan as a GSoC
rbultje
parents:
4874
diff
changeset
|
287 attr, value); |
774 | 288 /* Looking for a known attribute */ |
289 for (i = 0; attr_names[i].str; ++i) { | |
290 if (!strcasecmp(attr, attr_names[i].str)) { | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
291 if (attr_names[i].type == ATTR_NAME_TYPE_INT) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
292 *(int *)((char *)rtp_payload_data + |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
293 attr_names[i].offset) = atoi(value); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
294 } else if (attr_names[i].type == ATTR_NAME_TYPE_STR) |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
295 *(char **)((char *)rtp_payload_data + |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
296 attr_names[i].offset) = av_strdup(value); |
887 | 297 } |
0 | 298 } |
299 } | |
300 } | |
301 | |
5485 | 302 /** Parse a string p in the form of Range:npt=xx-xx, and determine the start |
1453
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
303 * and end time. |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
304 * Used for seeking in the rtp stream. |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
305 */ |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
306 static void rtsp_parse_range_npt(const char *p, int64_t *start, int64_t *end) |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
307 { |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
308 char buf[256]; |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
309 |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
310 skip_spaces(&p); |
2193
5ce5fad0dfac
replace the uses of old string functions that Reimar missed
mru
parents:
2189
diff
changeset
|
311 if (!av_stristart(p, "npt=", &p)) |
1453
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
312 return; |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
313 |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
314 *start = AV_NOPTS_VALUE; |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
315 *end = AV_NOPTS_VALUE; |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
316 |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
317 get_word_sep(buf, sizeof(buf), "-", &p); |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
318 *start = parse_date(buf, 1); |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
319 if (*p == '-') { |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
320 p++; |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
321 get_word_sep(buf, sizeof(buf), "-", &p); |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
322 *end = parse_date(buf, 1); |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
323 } |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
324 // av_log(NULL, AV_LOG_DEBUG, "Range Start: %lld\n", *start); |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
325 // av_log(NULL, AV_LOG_DEBUG, "Range End: %lld\n", *end); |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
326 } |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
327 |
0 | 328 typedef struct SDPParseState { |
329 /* SDP only */ | |
330 struct in_addr default_ip; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
331 int default_ttl; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
332 int skip_media; ///< set if an unknown m= line occurs |
0 | 333 } SDPParseState; |
334 | |
335 static void sdp_parse_line(AVFormatContext *s, SDPParseState *s1, | |
336 int letter, const char *buf) | |
337 { | |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
338 RTSPState *rt = s->priv_data; |
0 | 339 char buf1[64], st_type[64]; |
340 const char *p; | |
3967 | 341 enum CodecType codec_type; |
342 int payload_type, i; | |
0 | 343 AVStream *st; |
344 RTSPStream *rtsp_st; | |
345 struct in_addr sdp_ip; | |
346 int ttl; | |
347 | |
4990 | 348 dprintf(s, "sdp: %c='%s'\n", letter, buf); |
0 | 349 |
350 p = buf; | |
4281
f1d8951d6813
Skip m= blocks in the SDP if the media type is unknown. This prevents
rbultje
parents:
4251
diff
changeset
|
351 if (s1->skip_media && letter != 'm') |
f1d8951d6813
Skip m= blocks in the SDP if the media type is unknown. This prevents
rbultje
parents:
4251
diff
changeset
|
352 return; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
353 switch (letter) { |
0 | 354 case 'c': |
355 get_word(buf1, sizeof(buf1), &p); | |
356 if (strcmp(buf1, "IN") != 0) | |
357 return; | |
358 get_word(buf1, sizeof(buf1), &p); | |
359 if (strcmp(buf1, "IP4") != 0) | |
360 return; | |
361 get_word_sep(buf1, sizeof(buf1), "/", &p); | |
362 if (inet_aton(buf1, &sdp_ip) == 0) | |
363 return; | |
364 ttl = 16; | |
365 if (*p == '/') { | |
366 p++; | |
367 get_word_sep(buf1, sizeof(buf1), "/", &p); | |
368 ttl = atoi(buf1); | |
369 } | |
370 if (s->nb_streams == 0) { | |
371 s1->default_ip = sdp_ip; | |
372 s1->default_ttl = ttl; | |
373 } else { | |
374 st = s->streams[s->nb_streams - 1]; | |
375 rtsp_st = st->priv_data; | |
376 rtsp_st->sdp_ip = sdp_ip; | |
377 rtsp_st->sdp_ttl = ttl; | |
378 } | |
379 break; | |
380 case 's': | |
4361 | 381 av_metadata_set(&s->metadata, "title", p); |
0 | 382 break; |
383 case 'i': | |
384 if (s->nb_streams == 0) { | |
4361 | 385 av_metadata_set(&s->metadata, "comment", p); |
0 | 386 break; |
387 } | |
388 break; | |
389 case 'm': | |
390 /* new stream */ | |
4281
f1d8951d6813
Skip m= blocks in the SDP if the media type is unknown. This prevents
rbultje
parents:
4251
diff
changeset
|
391 s1->skip_media = 0; |
0 | 392 get_word(st_type, sizeof(st_type), &p); |
393 if (!strcmp(st_type, "audio")) { | |
394 codec_type = CODEC_TYPE_AUDIO; | |
395 } else if (!strcmp(st_type, "video")) { | |
396 codec_type = CODEC_TYPE_VIDEO; | |
4637
eaf90db8cc42
Recognize the "application" data type, which is required for WMS/UDP
rbultje
parents:
4557
diff
changeset
|
397 } else if (!strcmp(st_type, "application")) { |
eaf90db8cc42
Recognize the "application" data type, which is required for WMS/UDP
rbultje
parents:
4557
diff
changeset
|
398 codec_type = CODEC_TYPE_DATA; |
0 | 399 } else { |
4281
f1d8951d6813
Skip m= blocks in the SDP if the media type is unknown. This prevents
rbultje
parents:
4251
diff
changeset
|
400 s1->skip_media = 1; |
0 | 401 return; |
402 } | |
403 rtsp_st = av_mallocz(sizeof(RTSPStream)); | |
404 if (!rtsp_st) | |
405 return; | |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
406 rtsp_st->stream_index = -1; |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
407 dynarray_add(&rt->rtsp_streams, &rt->nb_rtsp_streams, rtsp_st); |
0 | 408 |
409 rtsp_st->sdp_ip = s1->default_ip; | |
410 rtsp_st->sdp_ttl = s1->default_ttl; | |
411 | |
412 get_word(buf1, sizeof(buf1), &p); /* port */ | |
413 rtsp_st->sdp_port = atoi(buf1); | |
414 | |
415 get_word(buf1, sizeof(buf1), &p); /* protocol (ignored) */ | |
885 | 416 |
0 | 417 /* XXX: handle list of formats */ |
418 get_word(buf1, sizeof(buf1), &p); /* format list */ | |
419 rtsp_st->sdp_payload_type = atoi(buf1); | |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
420 |
2759
b252e318023a
Remove the "AVRtpPayloadTypes[i].pt == i" assumption from RTP and RTSP
lucabe
parents:
2711
diff
changeset
|
421 if (!strcmp(ff_rtp_enc_name(rtsp_st->sdp_payload_type), "MP2T")) { |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
422 /* no corresponding stream */ |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
423 } else { |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
424 st = av_new_stream(s, 0); |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
425 if (!st) |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
426 return; |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
427 st->priv_data = rtsp_st; |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
428 rtsp_st->stream_index = st->index; |
820
feca73904e67
changing AVCodecContext codec -> *codec in AVStream so additions to AVCodecContext dont randomize AVStream and break binary compatibility
michael
parents:
774
diff
changeset
|
429 st->codec->codec_type = codec_type; |
774 | 430 if (rtsp_st->sdp_payload_type < RTP_PT_PRIVATE) { |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
431 /* if standard payload type, we can find the codec right now */ |
4519
f4b9967e0131
Remame rtp_get_codec_info() to ff_rtp_get_codec_info(), as it is not
lucabe
parents:
4514
diff
changeset
|
432 ff_rtp_get_codec_info(st->codec, rtsp_st->sdp_payload_type); |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
433 } |
0 | 434 } |
435 /* put a default control url */ | |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
436 av_strlcpy(rtsp_st->control_url, rt->control_uri, |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
437 sizeof(rtsp_st->control_url)); |
0 | 438 break; |
439 case 'a': | |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
440 if (av_strstart(p, "control:", &p)) { |
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
441 if (s->nb_streams == 0) { |
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
442 if (!strncmp(p, "rtsp://", 7)) |
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
443 av_strlcpy(rt->control_uri, p, |
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
444 sizeof(rt->control_uri)); |
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
445 } else { |
0 | 446 char proto[32]; |
447 /* get the control url */ | |
448 st = s->streams[s->nb_streams - 1]; | |
449 rtsp_st = st->priv_data; | |
885 | 450 |
0 | 451 /* XXX: may need to add full url resolution */ |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
452 url_split(proto, sizeof(proto), NULL, 0, NULL, 0, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
453 NULL, NULL, 0, p); |
0 | 454 if (proto[0] == '\0') { |
455 /* relative control URL */ | |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
456 if (rtsp_st->control_url[strlen(rtsp_st->control_url)-1]!='/') |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
457 av_strlcat(rtsp_st->control_url, "/", |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
458 sizeof(rtsp_st->control_url)); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
459 av_strlcat(rtsp_st->control_url, p, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
460 sizeof(rtsp_st->control_url)); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
461 } else |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
462 av_strlcpy(rtsp_st->control_url, p, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
463 sizeof(rtsp_st->control_url)); |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
464 } |
4185
023976c45ae1
Apply rtpmap: SDP lines to the last m= line only, since they generally just
rbultje
parents:
4182
diff
changeset
|
465 } else if (av_strstart(p, "rtpmap:", &p) && s->nb_streams > 0) { |
0 | 466 /* NOTE: rtpmap is only supported AFTER the 'm=' tag */ |
885 | 467 get_word(buf1, sizeof(buf1), &p); |
0 | 468 payload_type = atoi(buf1); |
4185
023976c45ae1
Apply rtpmap: SDP lines to the last m= line only, since they generally just
rbultje
parents:
4182
diff
changeset
|
469 st = s->streams[s->nb_streams - 1]; |
4186 | 470 rtsp_st = st->priv_data; |
5503
4ec7bcff8719
Add correct log context to av_log() calls in parse_rtpmap().
rbultje
parents:
5502
diff
changeset
|
471 sdp_parse_rtpmap(s, st->codec, rtsp_st, payload_type, p); |
2193
5ce5fad0dfac
replace the uses of old string functions that Reimar missed
mru
parents:
2189
diff
changeset
|
472 } else if (av_strstart(p, "fmtp:", &p)) { |
0 | 473 /* NOTE: fmtp is only supported AFTER the 'a=rtpmap:xxx' tag */ |
885 | 474 get_word(buf1, sizeof(buf1), &p); |
0 | 475 payload_type = atoi(buf1); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
476 for (i = 0; i < s->nb_streams; i++) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
477 st = s->streams[i]; |
0 | 478 rtsp_st = st->priv_data; |
479 if (rtsp_st->sdp_payload_type == payload_type) { | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
480 if (!(rtsp_st->dynamic_handler && |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
481 rtsp_st->dynamic_handler->parse_sdp_a_line && |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
482 rtsp_st->dynamic_handler->parse_sdp_a_line(s, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
483 i, rtsp_st->dynamic_protocol_context, buf))) |
1424
1c39ce5c6a5d
indentation fix, patch by Ryan Martell % rdm4 A martellventures P com %
gpoirier
parents:
1419
diff
changeset
|
484 sdp_parse_fmtp(st, p); |
0 | 485 } |
486 } | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
487 } else if (av_strstart(p, "framesize:", &p)) { |
1431
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
488 // let dynamic protocol handlers have a stab at the line. |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
489 get_word(buf1, sizeof(buf1), &p); |
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
490 payload_type = atoi(buf1); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
491 for (i = 0; i < s->nb_streams; i++) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
492 st = s->streams[i]; |
1431
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
493 rtsp_st = st->priv_data; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
494 if (rtsp_st->sdp_payload_type == payload_type && |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
495 rtsp_st->dynamic_handler && |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
496 rtsp_st->dynamic_handler->parse_sdp_a_line) |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
497 rtsp_st->dynamic_handler->parse_sdp_a_line(s, i, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
498 rtsp_st->dynamic_protocol_context, buf); |
1431
2d8a17631520
fix more dynamic protocol stuff, needed by the forthcoming h264
gpoirier
parents:
1425
diff
changeset
|
499 } |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
500 } else if (av_strstart(p, "range:", &p)) { |
1453
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
501 int64_t start, end; |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
502 |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
503 // this is so that seeking on a streamed file can work. |
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
504 rtsp_parse_range_npt(p, &start, &end); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
505 s->start_time = start; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
506 /* AV_NOPTS_VALUE means live broadcast (and can't seek) */ |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
507 s->duration = (end == AV_NOPTS_VALUE) ? |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
508 AV_NOPTS_VALUE : end - start; |
3960
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
509 } else if (av_strstart(p, "IsRealDataType:integer;",&p)) { |
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
510 if (atoi(p) == 1) |
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
511 rt->transport = RTSP_TRANSPORT_RDT; |
4744
51899c07a4f1
Add RTP/ASF header parsing, which is part of the SDP of these streams. See
rbultje
parents:
4667
diff
changeset
|
512 } else { |
51899c07a4f1
Add RTP/ASF header parsing, which is part of the SDP of these streams. See
rbultje
parents:
4667
diff
changeset
|
513 if (rt->server_type == RTSP_SERVER_WMS) |
51899c07a4f1
Add RTP/ASF header parsing, which is part of the SDP of these streams. See
rbultje
parents:
4667
diff
changeset
|
514 ff_wms_parse_sdp_a_line(s, p); |
51899c07a4f1
Add RTP/ASF header parsing, which is part of the SDP of these streams. See
rbultje
parents:
4667
diff
changeset
|
515 if (s->nb_streams > 0) { |
4745 | 516 if (rt->server_type == RTSP_SERVER_REAL) |
517 ff_real_parse_sdp_a_line(s, s->nb_streams - 1, p); | |
4163
8d6512cbd657
Parse the ASMRuleBook SDP line to dynamically create one new AVStream for
rbultje
parents:
4109
diff
changeset
|
518 |
4745 | 519 rtsp_st = s->streams[s->nb_streams - 1]->priv_data; |
520 if (rtsp_st->dynamic_handler && | |
521 rtsp_st->dynamic_handler->parse_sdp_a_line) | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
522 rtsp_st->dynamic_handler->parse_sdp_a_line(s, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
523 s->nb_streams - 1, |
4745 | 524 rtsp_st->dynamic_protocol_context, buf); |
4744
51899c07a4f1
Add RTP/ASF header parsing, which is part of the SDP of these streams. See
rbultje
parents:
4667
diff
changeset
|
525 } |
0 | 526 } |
527 break; | |
528 } | |
529 } | |
530 | |
64 | 531 static int sdp_parse(AVFormatContext *s, const char *content) |
0 | 532 { |
533 const char *p; | |
534 int letter; | |
4187 | 535 /* Some SDP lines, particularly for Realmedia or ASF RTSP streams, |
536 * contain long SDP lines containing complete ASF Headers (several | |
537 * kB) or arrays of MDPR (RM stream descriptor) headers plus | |
538 * "rulebooks" describing their properties. Therefore, the SDP line | |
4874
5370b0c1653c
Increase the SDP buffer size (again!) and also increase the temporary
rbultje
parents:
4789
diff
changeset
|
539 * buffer is large. |
5370b0c1653c
Increase the SDP buffer size (again!) and also increase the temporary
rbultje
parents:
4789
diff
changeset
|
540 * |
5370b0c1653c
Increase the SDP buffer size (again!) and also increase the temporary
rbultje
parents:
4789
diff
changeset
|
541 * The Vorbis FMTP line can be up to 16KB - see sdp_parse_fmtp. */ |
5370b0c1653c
Increase the SDP buffer size (again!) and also increase the temporary
rbultje
parents:
4789
diff
changeset
|
542 char buf[16384], *q; |
0 | 543 SDPParseState sdp_parse_state, *s1 = &sdp_parse_state; |
885 | 544 |
0 | 545 memset(s1, 0, sizeof(SDPParseState)); |
546 p = content; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
547 for (;;) { |
0 | 548 skip_spaces(&p); |
549 letter = *p; | |
550 if (letter == '\0') | |
551 break; | |
552 p++; | |
553 if (*p != '=') | |
554 goto next_line; | |
555 p++; | |
556 /* get the content */ | |
557 q = buf; | |
172 | 558 while (*p != '\n' && *p != '\r' && *p != '\0') { |
0 | 559 if ((q - buf) < sizeof(buf) - 1) |
560 *q++ = *p; | |
561 p++; | |
562 } | |
563 *q = '\0'; | |
564 sdp_parse_line(s, s1, letter, buf); | |
565 next_line: | |
566 while (*p != '\n' && *p != '\0') | |
567 p++; | |
568 if (*p == '\n') | |
569 p++; | |
570 } | |
571 return 0; | |
572 } | |
573 | |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
574 /* close and free RTSP streams */ |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
575 static void rtsp_close_streams(RTSPState *rt) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
576 { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
577 int i; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
578 RTSPStream *rtsp_st; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
579 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
580 for (i = 0; i < rt->nb_rtsp_streams; i++) { |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
581 rtsp_st = rt->rtsp_streams[i]; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
582 if (rtsp_st) { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
583 if (rtsp_st->transport_priv) { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
584 if (rt->transport == RTSP_TRANSPORT_RDT) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
585 ff_rdt_parse_close(rtsp_st->transport_priv); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
586 else |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
587 rtp_parse_close(rtsp_st->transport_priv); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
588 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
589 if (rtsp_st->rtp_handle) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
590 url_close(rtsp_st->rtp_handle); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
591 if (rtsp_st->dynamic_handler && rtsp_st->dynamic_protocol_context) |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
592 rtsp_st->dynamic_handler->close( |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
593 rtsp_st->dynamic_protocol_context); |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
594 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
595 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
596 av_free(rt->rtsp_streams); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
597 if (rt->asf_ctx) { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
598 av_close_input_stream (rt->asf_ctx); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
599 rt->asf_ctx = NULL; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
600 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
601 av_freep(&rt->auth_b64); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
602 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
603 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
604 static int rtsp_open_transport_ctx(AVFormatContext *s, RTSPStream *rtsp_st) |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
605 { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
606 RTSPState *rt = s->priv_data; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
607 AVStream *st = NULL; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
608 |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
609 /* open the RTP context */ |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
610 if (rtsp_st->stream_index >= 0) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
611 st = s->streams[rtsp_st->stream_index]; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
612 if (!st) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
613 s->ctx_flags |= AVFMTCTX_NOHEADER; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
614 |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
615 if (rt->transport == RTSP_TRANSPORT_RDT) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
616 rtsp_st->transport_priv = ff_rdt_parse_open(s, st->index, |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
617 rtsp_st->dynamic_protocol_context, |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
618 rtsp_st->dynamic_handler); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
619 else |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
620 rtsp_st->transport_priv = rtp_parse_open(s, st, rtsp_st->rtp_handle, |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
621 rtsp_st->sdp_payload_type, |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
622 &rtsp_st->rtp_payload_data); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
623 |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
624 if (!rtsp_st->transport_priv) { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
625 return AVERROR(ENOMEM); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
626 } else if (rt->transport != RTSP_TRANSPORT_RDT) { |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
627 if (rtsp_st->dynamic_handler) { |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
628 rtp_parse_set_dynamic_protocol(rtsp_st->transport_priv, |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
629 rtsp_st->dynamic_protocol_context, |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
630 rtsp_st->dynamic_handler); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
631 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
632 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
633 |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
634 return 0; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
635 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
636 |
5368
d93af9bfc0b8
Add some "#if"s to avoid compiling the RTSP code when the RTSP demuxer
lucabe
parents:
5366
diff
changeset
|
637 #if CONFIG_RTSP_DEMUXER |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
638 static int rtsp_probe(AVProbeData *p) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
639 { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
640 if (av_strstart(p->filename, "rtsp:", NULL)) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
641 return AVPROBE_SCORE_MAX; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
642 return 0; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
643 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
644 |
0 | 645 static void rtsp_parse_range(int *min_ptr, int *max_ptr, const char **pp) |
646 { | |
647 const char *p; | |
648 int v; | |
649 | |
650 p = *pp; | |
651 skip_spaces(&p); | |
652 v = strtol(p, (char **)&p, 10); | |
653 if (*p == '-') { | |
654 p++; | |
655 *min_ptr = v; | |
656 v = strtol(p, (char **)&p, 10); | |
657 *max_ptr = v; | |
658 } else { | |
659 *min_ptr = v; | |
660 *max_ptr = v; | |
661 } | |
662 *pp = p; | |
663 } | |
664 | |
665 /* XXX: only one transport specification is parsed */ | |
4557
bfe6fb676d46
Rename RTSPHeader to RTSPMessageHeader to reflect more clearly what the
rbultje
parents:
4549
diff
changeset
|
666 static void rtsp_parse_transport(RTSPMessageHeader *reply, const char *p) |
0 | 667 { |
668 char transport_protocol[16]; | |
669 char profile[16]; | |
670 char lower_transport[16]; | |
671 char parameter[16]; | |
672 RTSPTransportField *th; | |
673 char buf[256]; | |
885 | 674 |
0 | 675 reply->nb_transports = 0; |
885 | 676 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
677 for (;;) { |
0 | 678 skip_spaces(&p); |
679 if (*p == '\0') | |
680 break; | |
681 | |
682 th = &reply->transports[reply->nb_transports]; | |
683 | |
885 | 684 get_word_sep(transport_protocol, sizeof(transport_protocol), |
0 | 685 "/", &p); |
2865
51aa1054528c
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 2 x-pn-tng support
lu_zero
parents:
2864
diff
changeset
|
686 if (!strcasecmp (transport_protocol, "rtp")) { |
2866
ccbca87ccd5e
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 3 Reindent
lu_zero
parents:
2865
diff
changeset
|
687 get_word_sep(profile, sizeof(profile), "/;,", &p); |
ccbca87ccd5e
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 3 Reindent
lu_zero
parents:
2865
diff
changeset
|
688 lower_transport[0] = '\0'; |
ccbca87ccd5e
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 3 Reindent
lu_zero
parents:
2865
diff
changeset
|
689 /* rtp/avp/<protocol> */ |
ccbca87ccd5e
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 3 Reindent
lu_zero
parents:
2865
diff
changeset
|
690 if (*p == '/') { |
ccbca87ccd5e
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 3 Reindent
lu_zero
parents:
2865
diff
changeset
|
691 get_word_sep(lower_transport, sizeof(lower_transport), |
ccbca87ccd5e
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 3 Reindent
lu_zero
parents:
2865
diff
changeset
|
692 ";,", &p); |
3960
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
693 } |
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
694 th->transport = RTSP_TRANSPORT_RTP; |
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
695 } else if (!strcasecmp (transport_protocol, "x-pn-tng") || |
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
696 !strcasecmp (transport_protocol, "x-real-rdt")) { |
2866
ccbca87ccd5e
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 3 Reindent
lu_zero
parents:
2865
diff
changeset
|
697 /* x-pn-tng/<protocol> */ |
2865
51aa1054528c
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 2 x-pn-tng support
lu_zero
parents:
2864
diff
changeset
|
698 get_word_sep(lower_transport, sizeof(lower_transport), "/;,", &p); |
51aa1054528c
Real RTSP support, from Ronald S. Bultje rsbultje gmail - part 2 x-pn-tng support
lu_zero
parents:
2864
diff
changeset
|
699 profile[0] = '\0'; |
3960
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
700 th->transport = RTSP_TRANSPORT_RDT; |
0 | 701 } |
172 | 702 if (!strcasecmp(lower_transport, "TCP")) |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
703 th->lower_transport = RTSP_LOWER_TRANSPORT_TCP; |
0 | 704 else |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
705 th->lower_transport = RTSP_LOWER_TRANSPORT_UDP; |
885 | 706 |
0 | 707 if (*p == ';') |
708 p++; | |
709 /* get each parameter */ | |
710 while (*p != '\0' && *p != ',') { | |
711 get_word_sep(parameter, sizeof(parameter), "=;,", &p); | |
712 if (!strcmp(parameter, "port")) { | |
713 if (*p == '=') { | |
714 p++; | |
715 rtsp_parse_range(&th->port_min, &th->port_max, &p); | |
716 } | |
717 } else if (!strcmp(parameter, "client_port")) { | |
718 if (*p == '=') { | |
719 p++; | |
885 | 720 rtsp_parse_range(&th->client_port_min, |
0 | 721 &th->client_port_max, &p); |
722 } | |
723 } else if (!strcmp(parameter, "server_port")) { | |
724 if (*p == '=') { | |
725 p++; | |
885 | 726 rtsp_parse_range(&th->server_port_min, |
0 | 727 &th->server_port_max, &p); |
728 } | |
729 } else if (!strcmp(parameter, "interleaved")) { | |
730 if (*p == '=') { | |
731 p++; | |
885 | 732 rtsp_parse_range(&th->interleaved_min, |
0 | 733 &th->interleaved_max, &p); |
734 } | |
735 } else if (!strcmp(parameter, "multicast")) { | |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
736 if (th->lower_transport == RTSP_LOWER_TRANSPORT_UDP) |
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
737 th->lower_transport = RTSP_LOWER_TRANSPORT_UDP_MULTICAST; |
0 | 738 } else if (!strcmp(parameter, "ttl")) { |
739 if (*p == '=') { | |
740 p++; | |
741 th->ttl = strtol(p, (char **)&p, 10); | |
742 } | |
743 } else if (!strcmp(parameter, "destination")) { | |
744 struct in_addr ipaddr; | |
745 | |
746 if (*p == '=') { | |
747 p++; | |
748 get_word_sep(buf, sizeof(buf), ";,", &p); | |
885 | 749 if (inet_aton(buf, &ipaddr)) |
0 | 750 th->destination = ntohl(ipaddr.s_addr); |
751 } | |
752 } | |
753 while (*p != ';' && *p != '\0' && *p != ',') | |
754 p++; | |
755 if (*p == ';') | |
756 p++; | |
757 } | |
758 if (*p == ',') | |
759 p++; | |
760 | |
761 reply->nb_transports++; | |
762 } | |
763 } | |
764 | |
4557
bfe6fb676d46
Rename RTSPHeader to RTSPMessageHeader to reflect more clearly what the
rbultje
parents:
4549
diff
changeset
|
765 void rtsp_parse_line(RTSPMessageHeader *reply, const char *buf) |
0 | 766 { |
767 const char *p; | |
768 | |
769 /* NOTE: we do case independent match for broken servers */ | |
770 p = buf; | |
2193
5ce5fad0dfac
replace the uses of old string functions that Reimar missed
mru
parents:
2189
diff
changeset
|
771 if (av_stristart(p, "Session:", &p)) { |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
772 int t; |
0 | 773 get_word_sep(reply->session_id, sizeof(reply->session_id), ";", &p); |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
774 if (av_stristart(p, ";timeout=", &p) && |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
775 (t = strtol(p, NULL, 10)) > 0) { |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
776 reply->timeout = t; |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
777 } |
2193
5ce5fad0dfac
replace the uses of old string functions that Reimar missed
mru
parents:
2189
diff
changeset
|
778 } else if (av_stristart(p, "Content-Length:", &p)) { |
0 | 779 reply->content_length = strtol(p, NULL, 10); |
2193
5ce5fad0dfac
replace the uses of old string functions that Reimar missed
mru
parents:
2189
diff
changeset
|
780 } else if (av_stristart(p, "Transport:", &p)) { |
0 | 781 rtsp_parse_transport(reply, p); |
2193
5ce5fad0dfac
replace the uses of old string functions that Reimar missed
mru
parents:
2189
diff
changeset
|
782 } else if (av_stristart(p, "CSeq:", &p)) { |
0 | 783 reply->seq = strtol(p, NULL, 10); |
2193
5ce5fad0dfac
replace the uses of old string functions that Reimar missed
mru
parents:
2189
diff
changeset
|
784 } else if (av_stristart(p, "Range:", &p)) { |
1453
c0235bab9e92
Add support for getting duration of a RTP stream (for seeking in stream)
gpoirier
parents:
1431
diff
changeset
|
785 rtsp_parse_range_npt(p, &reply->range_start, &reply->range_end); |
3855 | 786 } else if (av_stristart(p, "RealChallenge1:", &p)) { |
787 skip_spaces(&p); | |
788 av_strlcpy(reply->real_challenge, p, sizeof(reply->real_challenge)); | |
4169
619845a9bab3
Use the "server" RTSP field to detect whether the server that we're talking
rbultje
parents:
4168
diff
changeset
|
789 } else if (av_stristart(p, "Server:", &p)) { |
619845a9bab3
Use the "server" RTSP field to detect whether the server that we're talking
rbultje
parents:
4168
diff
changeset
|
790 skip_spaces(&p); |
619845a9bab3
Use the "server" RTSP field to detect whether the server that we're talking
rbultje
parents:
4168
diff
changeset
|
791 av_strlcpy(reply->server, p, sizeof(reply->server)); |
5112
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
792 } else if (av_stristart(p, "Notice:", &p) || |
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
793 av_stristart(p, "X-Notice:", &p)) { |
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
794 reply->notice = strtol(p, NULL, 10); |
5333 | 795 } else if (av_stristart(p, "Location:", &p)) { |
796 skip_spaces(&p); | |
797 av_strlcpy(reply->location, p , sizeof(reply->location)); | |
0 | 798 } |
799 } | |
800 | |
179 | 801 /* skip a RTP/TCP interleaved packet */ |
802 static void rtsp_skip_packet(AVFormatContext *s) | |
803 { | |
804 RTSPState *rt = s->priv_data; | |
805 int ret, len, len1; | |
806 uint8_t buf[1024]; | |
807 | |
5004
84a7b7a2f252
Move function for reading whole specified amount of data from RTSP
kostya
parents:
4990
diff
changeset
|
808 ret = url_read_complete(rt->rtsp_hd, buf, 3); |
179 | 809 if (ret != 3) |
810 return; | |
2222 | 811 len = AV_RB16(buf + 1); |
4990 | 812 |
813 dprintf(s, "skipping RTP packet len=%d\n", len); | |
814 | |
179 | 815 /* skip payload */ |
816 while (len > 0) { | |
817 len1 = len; | |
818 if (len1 > sizeof(buf)) | |
819 len1 = sizeof(buf); | |
5004
84a7b7a2f252
Move function for reading whole specified amount of data from RTSP
kostya
parents:
4990
diff
changeset
|
820 ret = url_read_complete(rt->rtsp_hd, buf, len1); |
179 | 821 if (ret != len1) |
822 return; | |
823 len -= len1; | |
824 } | |
825 } | |
0 | 826 |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
827 /** |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
828 * Read a RTSP message from the server, or prepare to read data |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
829 * packets if we're reading data interleaved over the TCP/RTSP |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
830 * connection as well. |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
831 * |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
832 * @param s RTSP demuxer context |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
833 * @param reply pointer where the RTSP message header will be stored |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
834 * @param content_ptr pointer where the RTSP message body, if any, will |
5484
ee963dbe6ced
Remove residual use of the doxygen markup which is deprecated,
stefano
parents:
5480
diff
changeset
|
835 * be stored (length is in reply) |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
836 * @param return_on_interleaved_data whether the function may return if we |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
837 * encounter a data marker ('$'), which precedes data |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
838 * packets over interleaved TCP/RTSP connections. If this |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
839 * is set, this function will return 1 after encountering |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
840 * a '$'. If it is not set, the function will skip any |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
841 * data packets (if they are encountered), until a reply |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
842 * has been fully parsed. If no more data is available |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
843 * without parsing a reply, it will return an error. |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
844 * |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
845 * @returns 1 if a data packets is ready to be received, -1 on error, |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
846 * and 0 on success. |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
847 */ |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
848 static int rtsp_read_reply(AVFormatContext *s, RTSPMessageHeader *reply, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
849 unsigned char **content_ptr, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
850 int return_on_interleaved_data) |
0 | 851 { |
852 RTSPState *rt = s->priv_data; | |
853 char buf[4096], buf1[1024], *q; | |
854 unsigned char ch; | |
855 const char *p; | |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
856 int ret, content_length, line_count = 0; |
0 | 857 unsigned char *content = NULL; |
858 | |
4549 | 859 memset(reply, 0, sizeof(*reply)); |
0 | 860 |
861 /* parse reply (XXX: use buffers) */ | |
862 rt->last_reply[0] = '\0'; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
863 for (;;) { |
0 | 864 q = buf; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
865 for (;;) { |
5004
84a7b7a2f252
Move function for reading whole specified amount of data from RTSP
kostya
parents:
4990
diff
changeset
|
866 ret = url_read_complete(rt->rtsp_hd, &ch, 1); |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
867 #ifdef DEBUG_RTP_TCP |
4990 | 868 dprintf(s, "ret=%d c=%02x [%c]\n", ret, ch, ch); |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
869 #endif |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
870 if (ret != 1) |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
871 return -1; |
0 | 872 if (ch == '\n') |
873 break; | |
179 | 874 if (ch == '$') { |
875 /* XXX: only parse it if first char on line ? */ | |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
876 if (return_on_interleaved_data) { |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
877 return 1; |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
878 } else |
179 | 879 rtsp_skip_packet(s); |
880 } else if (ch != '\r') { | |
0 | 881 if ((q - buf) < sizeof(buf) - 1) |
882 *q++ = ch; | |
883 } | |
884 } | |
885 *q = '\0'; | |
4990 | 886 |
887 dprintf(s, "line='%s'\n", buf); | |
888 | |
0 | 889 /* test if last line */ |
890 if (buf[0] == '\0') | |
891 break; | |
892 p = buf; | |
893 if (line_count == 0) { | |
894 /* get reply code */ | |
895 get_word(buf1, sizeof(buf1), &p); | |
896 get_word(buf1, sizeof(buf1), &p); | |
897 reply->status_code = atoi(buf1); | |
898 } else { | |
899 rtsp_parse_line(reply, p); | |
2189 | 900 av_strlcat(rt->last_reply, p, sizeof(rt->last_reply)); |
901 av_strlcat(rt->last_reply, "\n", sizeof(rt->last_reply)); | |
0 | 902 } |
903 line_count++; | |
904 } | |
885 | 905 |
0 | 906 if (rt->session_id[0] == '\0' && reply->session_id[0] != '\0') |
2189 | 907 av_strlcpy(rt->session_id, reply->session_id, sizeof(rt->session_id)); |
885 | 908 |
0 | 909 content_length = reply->content_length; |
910 if (content_length > 0) { | |
911 /* leave some room for a trailing '\0' (useful for simple parsing) */ | |
912 content = av_malloc(content_length + 1); | |
5004
84a7b7a2f252
Move function for reading whole specified amount of data from RTSP
kostya
parents:
4990
diff
changeset
|
913 (void)url_read_complete(rt->rtsp_hd, content, content_length); |
0 | 914 content[content_length] = '\0'; |
915 } | |
916 if (content_ptr) | |
917 *content_ptr = content; | |
2263 | 918 else |
919 av_free(content); | |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
920 |
5112
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
921 /* EOS */ |
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
922 if (reply->notice == 2101 /* End-of-Stream Reached */ || |
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
923 reply->notice == 2104 /* Start-of-Stream Reached */ || |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
924 reply->notice == 2306 /* Continuous Feed Terminated */) { |
5112
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
925 rt->state = RTSP_STATE_IDLE; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
926 } else if (reply->notice >= 4400 && reply->notice < 5500) { |
5112
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
927 return AVERROR(EIO); /* data or server error */ |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
928 } else if (reply->notice == 2401 /* Ticket Expired */ || |
5112
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
929 (reply->notice >= 5500 && reply->notice < 5600) /* end of term */ ) |
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
930 return AVERROR(EPERM); |
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
931 |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
932 return 0; |
0 | 933 } |
934 | |
5572
820f0889bc45
Remove reply and content_ptr arguments from rtsp_send_cmd_async(), since
rbultje
parents:
5571
diff
changeset
|
935 static void rtsp_send_cmd_async(AVFormatContext *s, const char *cmd) |
4644
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
936 { |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
937 RTSPState *rt = s->priv_data; |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
938 char buf[4096], buf1[1024]; |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
939 |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
940 rt->seq++; |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
941 av_strlcpy(buf, cmd, sizeof(buf)); |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
942 snprintf(buf1, sizeof(buf1), "CSeq: %d\r\n", rt->seq); |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
943 av_strlcat(buf, buf1, sizeof(buf)); |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
944 if (rt->session_id[0] != '\0' && !strstr(cmd, "\nIf-Match:")) { |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
945 snprintf(buf1, sizeof(buf1), "Session: %s\r\n", rt->session_id); |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
946 av_strlcat(buf, buf1, sizeof(buf)); |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
947 } |
5220
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
948 if (rt->auth_b64) |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
949 av_strlcatf(buf, sizeof(buf), |
5221 | 950 "Authorization: Basic %s\r\n", |
951 rt->auth_b64); | |
4644
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
952 av_strlcat(buf, "\r\n", sizeof(buf)); |
4990 | 953 |
954 dprintf(s, "Sending:\n%s--\n", buf); | |
955 | |
4644
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
956 url_write(rt->rtsp_hd, buf, strlen(buf)); |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
957 rt->last_cmd_time = av_gettime(); |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
958 } |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
959 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
960 static void rtsp_send_cmd(AVFormatContext *s, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
961 const char *cmd, RTSPMessageHeader *reply, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
962 unsigned char **content_ptr) |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
963 { |
5572
820f0889bc45
Remove reply and content_ptr arguments from rtsp_send_cmd_async(), since
rbultje
parents:
5571
diff
changeset
|
964 rtsp_send_cmd_async(s, cmd); |
4644
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
965 |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
966 rtsp_read_reply(s, reply, content_ptr, 0); |
4644
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
967 } |
2962d395431b
Split rtsp_send_cmd() into two functions, one for the actual sending of the
rbultje
parents:
4641
diff
changeset
|
968 |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
969 /** |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
970 * @returns 0 on success, <0 on error, 1 if protocol is unavailable. |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
971 */ |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
972 static int make_setup_request(AVFormatContext *s, const char *host, int port, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
973 int lower_transport, const char *real_challenge) |
0 | 974 { |
975 RTSPState *rt = s->priv_data; | |
4638
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
976 int rtx, j, i, err, interleave = 0; |
0 | 977 RTSPStream *rtsp_st; |
4557
bfe6fb676d46
Rename RTSPHeader to RTSPMessageHeader to reflect more clearly what the
rbultje
parents:
4549
diff
changeset
|
978 RTSPMessageHeader reply1, *reply = &reply1; |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
979 char cmd[2048]; |
3876
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
980 const char *trans_pref; |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
981 |
3960
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
982 if (rt->transport == RTSP_TRANSPORT_RDT) |
3876
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
983 trans_pref = "x-pn-tng"; |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
984 else |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
985 trans_pref = "RTP/AVP"; |
885 | 986 |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
987 /* default timeout: 1 minute */ |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
988 rt->timeout = 60; |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
989 |
0 | 990 /* for each stream, make the setup request */ |
991 /* XXX: we assume the same server is used for the control of each | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
992 * RTSP stream */ |
774 | 993 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
994 for (j = RTSP_RTP_PORT_MIN, i = 0; i < rt->nb_rtsp_streams; ++i) { |
0 | 995 char transport[2048]; |
996 | |
4638
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
997 /** |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
998 * WMS serves all UDP data over a single connection, the RTX, which |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
999 * isn't necessarily the first in the SDP but has to be the first |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1000 * to be set up, else the second/third SETUP will fail with a 461. |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1001 */ |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1002 if (lower_transport == RTSP_LOWER_TRANSPORT_UDP && |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1003 rt->server_type == RTSP_SERVER_WMS) { |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1004 if (i == 0) { |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1005 /* rtx first */ |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1006 for (rtx = 0; rtx < rt->nb_rtsp_streams; rtx++) { |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1007 int len = strlen(rt->rtsp_streams[rtx]->control_url); |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1008 if (len >= 4 && |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1009 !strcmp(rt->rtsp_streams[rtx]->control_url + len - 4, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1010 "/rtx")) |
4638
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1011 break; |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1012 } |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1013 if (rtx == rt->nb_rtsp_streams) |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1014 return -1; /* no RTX found */ |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1015 rtsp_st = rt->rtsp_streams[rtx]; |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1016 } else |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1017 rtsp_st = rt->rtsp_streams[i > rtx ? i : i - 1]; |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1018 } else |
4639 | 1019 rtsp_st = rt->rtsp_streams[i]; |
0 | 1020 |
1021 /* RTP/UDP */ | |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1022 if (lower_transport == RTSP_LOWER_TRANSPORT_UDP) { |
0 | 1023 char buf[256]; |
1024 | |
4638
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1025 if (rt->server_type == RTSP_SERVER_WMS && i > 1) { |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1026 port = reply->transports[0].client_port_min; |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1027 goto have_port; |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1028 } |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1029 |
0 | 1030 /* first try in specified port range */ |
774 | 1031 if (RTSP_RTP_PORT_MIN != 0) { |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1032 while (j <= RTSP_RTP_PORT_MAX) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1033 snprintf(buf, sizeof(buf), "rtp://%s?localport=%d", |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1034 host, j); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1035 /* we will use two ports per rtp stream (rtp and rtcp) */ |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1036 j += 2; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1037 if (url_open(&rtsp_st->rtp_handle, buf, URL_RDWR) == 0) |
0 | 1038 goto rtp_opened; |
1039 } | |
1040 } | |
1041 | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1042 #if 0 |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1043 /* then try on any port */ |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1044 if (url_open(&rtsp_st->rtp_handle, "rtp://", URL_RDONLY) < 0) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1045 err = AVERROR_INVALIDDATA; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1046 goto fail; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1047 } |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1048 #endif |
0 | 1049 |
1050 rtp_opened: | |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1051 port = rtp_get_local_port(rtsp_st->rtp_handle); |
4638
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1052 have_port: |
3877
3e0c7ad2a675
Remove unused code that used to handle protocol concatenation, i.e. trying
rbultje
parents:
3876
diff
changeset
|
1053 snprintf(transport, sizeof(transport) - 1, |
3958
ab2d2bc3a6e7
Send improper UDP SETUP request, which is what Realmedia servers expect.
rbultje
parents:
3957
diff
changeset
|
1054 "%s/UDP;", trans_pref); |
ab2d2bc3a6e7
Send improper UDP SETUP request, which is what Realmedia servers expect.
rbultje
parents:
3957
diff
changeset
|
1055 if (rt->server_type != RTSP_SERVER_REAL) |
ab2d2bc3a6e7
Send improper UDP SETUP request, which is what Realmedia servers expect.
rbultje
parents:
3957
diff
changeset
|
1056 av_strlcat(transport, "unicast;", sizeof(transport)); |
ab2d2bc3a6e7
Send improper UDP SETUP request, which is what Realmedia servers expect.
rbultje
parents:
3957
diff
changeset
|
1057 av_strlcatf(transport, sizeof(transport), |
ab2d2bc3a6e7
Send improper UDP SETUP request, which is what Realmedia servers expect.
rbultje
parents:
3957
diff
changeset
|
1058 "client_port=%d", port); |
4638
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1059 if (rt->transport == RTSP_TRANSPORT_RTP && |
801468f16243
Make RTSP-MS-over-UDP negotiation work. See "[PATCH] RTSP-MS 8/15: fix
rbultje
parents:
4637
diff
changeset
|
1060 !(rt->server_type == RTSP_SERVER_WMS && i > 0)) |
3876
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1061 av_strlcatf(transport, sizeof(transport), "-%d", port + 1); |
0 | 1062 } |
1063 | |
1064 /* RTP/TCP */ | |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1065 else if (lower_transport == RTSP_LOWER_TRANSPORT_TCP) { |
4637
eaf90db8cc42
Recognize the "application" data type, which is required for WMS/UDP
rbultje
parents:
4557
diff
changeset
|
1066 /** For WMS streams, the application streams are only used for |
eaf90db8cc42
Recognize the "application" data type, which is required for WMS/UDP
rbultje
parents:
4557
diff
changeset
|
1067 * UDP. When trying to set it up for TCP streams, the server |
eaf90db8cc42
Recognize the "application" data type, which is required for WMS/UDP
rbultje
parents:
4557
diff
changeset
|
1068 * will return an error. Therefore, we skip those streams. */ |
eaf90db8cc42
Recognize the "application" data type, which is required for WMS/UDP
rbultje
parents:
4557
diff
changeset
|
1069 if (rt->server_type == RTSP_SERVER_WMS && |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1070 s->streams[rtsp_st->stream_index]->codec->codec_type == |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1071 CODEC_TYPE_DATA) |
4637
eaf90db8cc42
Recognize the "application" data type, which is required for WMS/UDP
rbultje
parents:
4557
diff
changeset
|
1072 continue; |
3877
3e0c7ad2a675
Remove unused code that used to handle protocol concatenation, i.e. trying
rbultje
parents:
3876
diff
changeset
|
1073 snprintf(transport, sizeof(transport) - 1, |
4332
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1074 "%s/TCP;", trans_pref); |
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1075 if (rt->server_type == RTSP_SERVER_WMS) |
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1076 av_strlcat(transport, "unicast;", sizeof(transport)); |
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1077 av_strlcatf(transport, sizeof(transport), |
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1078 "interleaved=%d-%d", |
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1079 interleave, interleave + 1); |
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1080 interleave += 2; |
0 | 1081 } |
1082 | |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1083 else if (lower_transport == RTSP_LOWER_TRANSPORT_UDP_MULTICAST) { |
3877
3e0c7ad2a675
Remove unused code that used to handle protocol concatenation, i.e. trying
rbultje
parents:
3876
diff
changeset
|
1084 snprintf(transport, sizeof(transport) - 1, |
3876
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1085 "%s/UDP;multicast", trans_pref); |
0 | 1086 } |
4332
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1087 if (rt->server_type == RTSP_SERVER_REAL || |
0d776969b708
Fix the Transport: line in the SETUP request so that it works with WMS
rbultje
parents:
4291
diff
changeset
|
1088 rt->server_type == RTSP_SERVER_WMS) |
3876
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1089 av_strlcat(transport, ";mode=play", sizeof(transport)); |
885 | 1090 snprintf(cmd, sizeof(cmd), |
172 | 1091 "SETUP %s RTSP/1.0\r\n" |
1092 "Transport: %s\r\n", | |
0 | 1093 rtsp_st->control_url, transport); |
3923
83e51bcb03c2
Rename RTSP_SERVER_RDT to RTSP_SERVER_REAL, because RDT (the transport
rbultje
parents:
3920
diff
changeset
|
1094 if (i == 0 && rt->server_type == RTSP_SERVER_REAL) { |
3876
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1095 char real_res[41], real_csum[9]; |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1096 ff_rdt_calc_response_and_checksum(real_res, real_csum, |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1097 real_challenge); |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1098 av_strlcatf(cmd, sizeof(cmd), |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1099 "If-Match: %s\r\n" |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1100 "RealChallenge2: %s, sd=%s\r\n", |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1101 rt->session_id, real_res, real_csum); |
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1102 } |
0 | 1103 rtsp_send_cmd(s, cmd, reply, NULL); |
3149
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1104 if (reply->status_code == 461 /* Unsupported protocol */ && i == 0) { |
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1105 err = 1; |
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1106 goto fail; |
3151 | 1107 } else if (reply->status_code != RTSP_STATUS_OK || |
1108 reply->nb_transports != 1) { | |
0 | 1109 err = AVERROR_INVALIDDATA; |
1110 goto fail; | |
1111 } | |
1112 | |
1113 /* XXX: same protocol for all streams is required */ | |
1114 if (i > 0) { | |
3960
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
1115 if (reply->transports[0].lower_transport != rt->lower_transport || |
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
1116 reply->transports[0].transport != rt->transport) { |
0 | 1117 err = AVERROR_INVALIDDATA; |
1118 goto fail; | |
1119 } | |
1120 } else { | |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1121 rt->lower_transport = reply->transports[0].lower_transport; |
3960
13e9b0d3a314
Implement a RTSPTransport field, which allows proper separation of server
rbultje
parents:
3959
diff
changeset
|
1122 rt->transport = reply->transports[0].transport; |
0 | 1123 } |
1124 | |
1125 /* close RTP connection if not choosen */ | |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1126 if (reply->transports[0].lower_transport != RTSP_LOWER_TRANSPORT_UDP && |
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1127 (lower_transport == RTSP_LOWER_TRANSPORT_UDP)) { |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1128 url_close(rtsp_st->rtp_handle); |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1129 rtsp_st->rtp_handle = NULL; |
0 | 1130 } |
1131 | |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1132 switch(reply->transports[0].lower_transport) { |
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1133 case RTSP_LOWER_TRANSPORT_TCP: |
0 | 1134 rtsp_st->interleaved_min = reply->transports[0].interleaved_min; |
1135 rtsp_st->interleaved_max = reply->transports[0].interleaved_max; | |
1136 break; | |
885 | 1137 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1138 case RTSP_LOWER_TRANSPORT_UDP: { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1139 char url[1024]; |
885 | 1140 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1141 /* XXX: also use address if specified */ |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1142 snprintf(url, sizeof(url), "rtp://%s:%d", |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1143 host, reply->transports[0].server_port_min); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1144 if (!(rt->server_type == RTSP_SERVER_WMS && i > 1) && |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1145 rtp_set_remote_url(rtsp_st->rtp_handle, url) < 0) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1146 err = AVERROR_INVALIDDATA; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1147 goto fail; |
0 | 1148 } |
1149 break; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1150 } |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1151 case RTSP_LOWER_TRANSPORT_UDP_MULTICAST: { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1152 char url[1024]; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1153 struct in_addr in; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1154 int port, ttl; |
0 | 1155 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1156 if (reply->transports[0].destination) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1157 in.s_addr = htonl(reply->transports[0].destination); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1158 port = reply->transports[0].port_min; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1159 ttl = reply->transports[0].ttl; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1160 } else { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1161 in = rtsp_st->sdp_ip; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1162 port = rtsp_st->sdp_port; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1163 ttl = rtsp_st->sdp_ttl; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1164 } |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1165 snprintf(url, sizeof(url), "rtp://%s:%d?ttl=%d", |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1166 inet_ntoa(in), port, ttl); |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1167 if (url_open(&rtsp_st->rtp_handle, url, URL_RDWR) < 0) { |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1168 err = AVERROR_INVALIDDATA; |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1169 goto fail; |
0 | 1170 } |
1171 break; | |
1172 } | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1173 } |
774 | 1174 |
3919
1879eab34f88
Factorize out common code for opening of the RTP parsing context between
rbultje
parents:
3905
diff
changeset
|
1175 if ((err = rtsp_open_transport_ctx(s, rtsp_st))) |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1176 goto fail; |
0 | 1177 } |
1178 | |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1179 if (reply->timeout > 0) |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1180 rt->timeout = reply->timeout; |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1181 |
3923
83e51bcb03c2
Rename RTSP_SERVER_RDT to RTSP_SERVER_REAL, because RDT (the transport
rbultje
parents:
3920
diff
changeset
|
1182 if (rt->server_type == RTSP_SERVER_REAL) |
3903
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1183 rt->need_subscription = 1; |
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1184 |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1185 return 0; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1186 |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1187 fail: |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1188 for (i = 0; i < rt->nb_rtsp_streams; i++) { |
3149
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1189 if (rt->rtsp_streams[i]->rtp_handle) { |
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1190 url_close(rt->rtsp_streams[i]->rtp_handle); |
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1191 rt->rtsp_streams[i]->rtp_handle = NULL; |
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1192 } |
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1193 } |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1194 return err; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1195 } |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1196 |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1197 static int rtsp_read_play(AVFormatContext *s) |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1198 { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1199 RTSPState *rt = s->priv_data; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1200 RTSPMessageHeader reply1, *reply = &reply1; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1201 char cmd[1024]; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1202 |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1203 av_log(s, AV_LOG_DEBUG, "hello state=%d\n", rt->state); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1204 |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1205 if (!(rt->server_type == RTSP_SERVER_REAL && rt->need_subscription)) { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1206 if (rt->state == RTSP_STATE_PAUSED) { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1207 snprintf(cmd, sizeof(cmd), |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1208 "PLAY %s RTSP/1.0\r\n", |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
1209 rt->control_uri); |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1210 } else { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1211 snprintf(cmd, sizeof(cmd), |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1212 "PLAY %s RTSP/1.0\r\n" |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1213 "Range: npt=%0.3f-\r\n", |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
1214 rt->control_uri, |
5365
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1215 (double)rt->seek_timestamp / AV_TIME_BASE); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1216 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1217 rtsp_send_cmd(s, cmd, reply, NULL); |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1218 if (reply->status_code != RTSP_STATUS_OK) { |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1219 return -1; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1220 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1221 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1222 rt->state = RTSP_STATE_PLAYING; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1223 return 0; |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1224 } |
4097dc22e612
Move some some functions around, so that splitting the SDP code out of
lucabe
parents:
5334
diff
changeset
|
1225 |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1226 static int rtsp_read_header(AVFormatContext *s, |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1227 AVFormatParameters *ap) |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1228 { |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1229 RTSPState *rt = s->priv_data; |
5331 | 1230 char host[1024], path[1024], tcpname[1024], cmd[2048], auth[128]; |
1231 char *option_list, *option, *filename; | |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1232 URLContext *rtsp_hd; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1233 int port, ret, err; |
4557
bfe6fb676d46
Rename RTSPHeader to RTSPMessageHeader to reflect more clearly what the
rbultje
parents:
4549
diff
changeset
|
1234 RTSPMessageHeader reply1, *reply = &reply1; |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1235 unsigned char *content = NULL; |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1236 int lower_transport_mask = 0; |
3856 | 1237 char real_challenge[64]; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1238 redirect: |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1239 /* extract hostname and port */ |
5220
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1240 url_split(NULL, 0, auth, sizeof(auth), |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1241 host, sizeof(host), &port, path, sizeof(path), s->filename); |
5220
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1242 if (*auth) { |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1243 int auth_len = strlen(auth), b64_len = ((auth_len + 2) / 3) * 4 + 1; |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1244 |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1245 if (!(rt->auth_b64 = av_malloc(b64_len))) |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1246 return AVERROR(ENOMEM); |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1247 if (!av_base64_encode(rt->auth_b64, b64_len, auth, auth_len)) { |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1248 err = AVERROR(EINVAL); |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1249 goto fail; |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1250 } |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1251 } |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1252 if (port < 0) |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1253 port = RTSP_DEFAULT_PORT; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1254 |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1255 /* search for options */ |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1256 option_list = strchr(path, '?'); |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1257 if (option_list) { |
5331 | 1258 filename = strchr(s->filename, '?'); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1259 while (option_list) { |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1260 /* move the option pointer */ |
5331 | 1261 option = ++option_list; |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1262 option_list = strchr(option_list, '&'); |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1263 if (option_list) |
5331 | 1264 *option_list = 0; |
1265 | |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1266 /* handle the options */ |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1267 if (!strcmp(option, "udp")) { |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1268 lower_transport_mask = (1<< RTSP_LOWER_TRANSPORT_UDP); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1269 } else if (!strcmp(option, "multicast")) { |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1270 lower_transport_mask = (1<< RTSP_LOWER_TRANSPORT_UDP_MULTICAST); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1271 } else if (!strcmp(option, "tcp")) { |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1272 lower_transport_mask = (1<< RTSP_LOWER_TRANSPORT_TCP); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1273 } else { |
5331 | 1274 strcpy(++filename, option); |
1275 filename += strlen(option); | |
1276 if (option_list) *filename = '&'; | |
1277 } | |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1278 } |
5331 | 1279 *filename = 0; |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1280 } |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1281 |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1282 if (!lower_transport_mask) |
4514
2a84d46427d1
Rename RTSP_*_LAST to RTSP_*_NB in line with PIX_FMT_* in lavc. See "[PATCH]
rbultje
parents:
4388
diff
changeset
|
1283 lower_transport_mask = (1 << RTSP_LOWER_TRANSPORT_NB) - 1; |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1284 |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1285 /* open the tcp connexion */ |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1286 snprintf(tcpname, sizeof(tcpname), "tcp://%s:%d", host, port); |
5220
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1287 if (url_open(&rtsp_hd, tcpname, URL_RDWR) < 0) { |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1288 err = AVERROR(EIO); |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1289 goto fail; |
cad276e8f96e
RTSP basic authentication, patch originally by Philip Coombes
rbultje
parents:
5112
diff
changeset
|
1290 } |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1291 rt->rtsp_hd = rtsp_hd; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1292 rt->seq = 0; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1293 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1294 /* request options supported by the server; this also detects server |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1295 * type */ |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
1296 av_strlcpy(rt->control_uri, s->filename, |
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
1297 sizeof(rt->control_uri)); |
3856 | 1298 for (rt->server_type = RTSP_SERVER_RTP;;) { |
1299 snprintf(cmd, sizeof(cmd), | |
1300 "OPTIONS %s RTSP/1.0\r\n", s->filename); | |
3923
83e51bcb03c2
Rename RTSP_SERVER_RDT to RTSP_SERVER_REAL, because RDT (the transport
rbultje
parents:
3920
diff
changeset
|
1301 if (rt->server_type == RTSP_SERVER_REAL) |
3856 | 1302 av_strlcat(cmd, |
1303 /** | |
1304 * The following entries are required for proper | |
1305 * streaming from a Realmedia server. They are | |
1306 * interdependent in some way although we currently | |
1307 * don't quite understand how. Values were copied | |
1308 * from mplayer SVN r23589. | |
1309 * @param CompanyID is a 16-byte ID in base64 | |
1310 * @param ClientChallenge is a 16-byte ID in hex | |
1311 */ | |
1312 "ClientChallenge: 9e26d33f2984236010ef6253fb1887f7\r\n" | |
1313 "PlayerStarttime: [28/03/2003:22:50:23 00:00]\r\n" | |
1314 "CompanyID: KnKV4M4I/B2FjJ1TToLycw==\r\n" | |
1315 "GUID: 00000000-0000-0000-0000-000000000000\r\n", | |
1316 sizeof(cmd)); | |
1317 rtsp_send_cmd(s, cmd, reply, NULL); | |
1318 if (reply->status_code != RTSP_STATUS_OK) { | |
1319 err = AVERROR_INVALIDDATA; | |
1320 goto fail; | |
1321 } | |
1322 | |
1323 /* detect server type if not standard-compliant RTP */ | |
3923
83e51bcb03c2
Rename RTSP_SERVER_RDT to RTSP_SERVER_REAL, because RDT (the transport
rbultje
parents:
3920
diff
changeset
|
1324 if (rt->server_type != RTSP_SERVER_REAL && reply->real_challenge[0]) { |
83e51bcb03c2
Rename RTSP_SERVER_RDT to RTSP_SERVER_REAL, because RDT (the transport
rbultje
parents:
3920
diff
changeset
|
1325 rt->server_type = RTSP_SERVER_REAL; |
3856 | 1326 continue; |
4169
619845a9bab3
Use the "server" RTSP field to detect whether the server that we're talking
rbultje
parents:
4168
diff
changeset
|
1327 } else if (!strncasecmp(reply->server, "WMServer/", 9)) { |
619845a9bab3
Use the "server" RTSP field to detect whether the server that we're talking
rbultje
parents:
4168
diff
changeset
|
1328 rt->server_type = RTSP_SERVER_WMS; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1329 } else if (rt->server_type == RTSP_SERVER_REAL) |
3856 | 1330 strcpy(real_challenge, reply->real_challenge); |
1331 break; | |
1332 } | |
1333 | |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1334 /* describe the stream */ |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1335 snprintf(cmd, sizeof(cmd), |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1336 "DESCRIBE %s RTSP/1.0\r\n" |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1337 "Accept: application/sdp\r\n", |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1338 s->filename); |
3923
83e51bcb03c2
Rename RTSP_SERVER_RDT to RTSP_SERVER_REAL, because RDT (the transport
rbultje
parents:
3920
diff
changeset
|
1339 if (rt->server_type == RTSP_SERVER_REAL) { |
3859 | 1340 /** |
1341 * The Require: attribute is needed for proper streaming from | |
1342 * Realmedia servers. | |
1343 */ | |
1344 av_strlcat(cmd, | |
1345 "Require: com.real.retain-entity-for-setup\r\n", | |
1346 sizeof(cmd)); | |
1347 } | |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1348 rtsp_send_cmd(s, cmd, reply, &content); |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1349 if (!content) { |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1350 err = AVERROR_INVALIDDATA; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1351 goto fail; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1352 } |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1353 if (reply->status_code != RTSP_STATUS_OK) { |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1354 err = AVERROR_INVALIDDATA; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1355 goto fail; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1356 } |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1357 |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1358 /* now we got the SDP description, we parse it */ |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1359 ret = sdp_parse(s, (const char *)content); |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1360 av_freep(&content); |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1361 if (ret < 0) { |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1362 err = AVERROR_INVALIDDATA; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1363 goto fail; |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1364 } |
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1365 |
3149
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1366 do { |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1367 int lower_transport = ff_log2_tab[lower_transport_mask & |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1368 ~(lower_transport_mask - 1)]; |
3149
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1369 |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1370 err = make_setup_request(s, host, port, lower_transport, |
3923
83e51bcb03c2
Rename RTSP_SERVER_RDT to RTSP_SERVER_REAL, because RDT (the transport
rbultje
parents:
3920
diff
changeset
|
1371 rt->server_type == RTSP_SERVER_REAL ? |
3876
1026953d4ffe
Implement Realmedia/RTSP-compatible SETUP command. This includes calculation
rbultje
parents:
3861
diff
changeset
|
1372 real_challenge : NULL); |
3149
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1373 if (err < 0) |
3151 | 1374 goto fail; |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1375 lower_transport_mask &= ~(1 << lower_transport); |
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1376 if (lower_transport_mask == 0 && err == 1) { |
3202
98e633b72d38
use FF_NETERROR to make winsock happy, patch from prossATxvidDoTorg
lu_zero
parents:
3151
diff
changeset
|
1377 err = AVERROR(FF_NETERROR(EPROTONOSUPPORT)); |
3149
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1378 goto fail; |
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1379 } |
5a7a7406ab1f
Allow cycling between different protocols (TCP, UDP or multicast) so that if
rbultje
parents:
3147
diff
changeset
|
1380 } while (err); |
3147
91d65fdf91e1
Split the SETUP request into a separate function, as a prelude into allowing
rbultje
parents:
2884
diff
changeset
|
1381 |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1382 rt->state = RTSP_STATE_IDLE; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1383 rt->seek_timestamp = 0; /* default is to start stream at position zero */ |
1003 | 1384 if (ap->initial_pause) { |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1385 /* do not start immediately */ |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1386 } else { |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1387 if (rtsp_read_play(s) < 0) { |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1388 err = AVERROR_INVALIDDATA; |
0 | 1389 goto fail; |
1390 } | |
1391 } | |
1392 return 0; | |
1393 fail: | |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1394 rtsp_close_streams(rt); |
0 | 1395 av_freep(&content); |
1396 url_close(rt->rtsp_hd); | |
5333 | 1397 if (reply->status_code >=300 && reply->status_code < 400) { |
1398 av_strlcpy(s->filename, reply->location, sizeof(s->filename)); | |
1399 av_log(s, AV_LOG_INFO, "Status %d: Redirecting to %s\n", | |
1400 reply->status_code, | |
1401 s->filename); | |
1402 goto redirect; | |
1403 } | |
0 | 1404 return err; |
1405 } | |
1406 | |
5493 | 1407 static int udp_read_packet(AVFormatContext *s, RTSPStream **prtsp_st, |
1408 uint8_t *buf, int buf_size) | |
1409 { | |
1410 RTSPState *rt = s->priv_data; | |
1411 RTSPStream *rtsp_st; | |
1412 fd_set rfds; | |
1413 int fd, fd_max, n, i, ret, tcp_fd; | |
1414 struct timeval tv; | |
1415 | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1416 for (;;) { |
5493 | 1417 if (url_interrupt_cb()) |
1418 return AVERROR(EINTR); | |
1419 FD_ZERO(&rfds); | |
1420 if (rt->rtsp_hd) { | |
1421 tcp_fd = fd_max = url_get_file_handle(rt->rtsp_hd); | |
1422 FD_SET(tcp_fd, &rfds); | |
1423 } else { | |
1424 fd_max = 0; | |
1425 tcp_fd = -1; | |
1426 } | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1427 for (i = 0; i < rt->nb_rtsp_streams; i++) { |
5493 | 1428 rtsp_st = rt->rtsp_streams[i]; |
1429 if (rtsp_st->rtp_handle) { | |
1430 /* currently, we cannot probe RTCP handle because of | |
1431 * blocking restrictions */ | |
1432 fd = url_get_file_handle(rtsp_st->rtp_handle); | |
1433 if (fd > fd_max) | |
1434 fd_max = fd; | |
1435 FD_SET(fd, &rfds); | |
1436 } | |
1437 } | |
1438 tv.tv_sec = 0; | |
1439 tv.tv_usec = 100 * 1000; | |
1440 n = select(fd_max + 1, &rfds, NULL, NULL, &tv); | |
1441 if (n > 0) { | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1442 for (i = 0; i < rt->nb_rtsp_streams; i++) { |
5493 | 1443 rtsp_st = rt->rtsp_streams[i]; |
1444 if (rtsp_st->rtp_handle) { | |
1445 fd = url_get_file_handle(rtsp_st->rtp_handle); | |
1446 if (FD_ISSET(fd, &rfds)) { | |
1447 ret = url_read(rtsp_st->rtp_handle, buf, buf_size); | |
1448 if (ret > 0) { | |
1449 *prtsp_st = rtsp_st; | |
1450 return ret; | |
1451 } | |
1452 } | |
1453 } | |
1454 } | |
1455 #if CONFIG_RTSP_DEMUXER | |
5589
dca2836e09b8
Don't use tcp_fd if we're not using TCP-based connections (e.g. when
rbultje
parents:
5574
diff
changeset
|
1456 if (tcp_fd != -1 && FD_ISSET(tcp_fd, &rfds)) { |
5493 | 1457 RTSPMessageHeader reply; |
1458 | |
1459 rtsp_read_reply(s, &reply, NULL, 0); | |
1460 /* XXX: parse message */ | |
1461 if (rt->state != RTSP_STATE_PLAYING) | |
1462 return 0; | |
1463 } | |
1464 #endif | |
1465 } | |
1466 } | |
1467 } | |
1468 | |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1469 static int tcp_read_packet(AVFormatContext *s, RTSPStream **prtsp_st, |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1470 uint8_t *buf, int buf_size) |
0 | 1471 { |
1472 RTSPState *rt = s->priv_data; | |
172 | 1473 int id, len, i, ret; |
0 | 1474 RTSPStream *rtsp_st; |
1475 | |
172 | 1476 #ifdef DEBUG_RTP_TCP |
4990 | 1477 dprintf(s, "tcp_read_packet:\n"); |
172 | 1478 #endif |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1479 redo: |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1480 for (;;) { |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
1481 RTSPMessageHeader reply; |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
1482 |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
1483 ret = rtsp_read_reply(s, &reply, NULL, 1); |
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
1484 if (ret == -1) |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1485 return -1; |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
1486 if (ret == 1) /* received '$' */ |
0 | 1487 break; |
4772
fb0b1e68356c
Allow (and parse) incoming server messages (notices) interleaved with TCP
rbultje
parents:
4745
diff
changeset
|
1488 /* XXX: parse message */ |
5112
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
1489 if (rt->state != RTSP_STATE_PLAYING) |
85e0a9761818
Implement support for EOS as used by WMS and other RTSP servers that do not
rbultje
parents:
5013
diff
changeset
|
1490 return 0; |
0 | 1491 } |
5004
84a7b7a2f252
Move function for reading whole specified amount of data from RTSP
kostya
parents:
4990
diff
changeset
|
1492 ret = url_read_complete(rt->rtsp_hd, buf, 3); |
172 | 1493 if (ret != 3) |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1494 return -1; |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1495 id = buf[0]; |
2222 | 1496 len = AV_RB16(buf + 1); |
172 | 1497 #ifdef DEBUG_RTP_TCP |
4990 | 1498 dprintf(s, "id=%d len=%d\n", id, len); |
172 | 1499 #endif |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1500 if (len > buf_size || len < 12) |
0 | 1501 goto redo; |
1502 /* get the data */ | |
5004
84a7b7a2f252
Move function for reading whole specified amount of data from RTSP
kostya
parents:
4990
diff
changeset
|
1503 ret = url_read_complete(rt->rtsp_hd, buf, len); |
172 | 1504 if (ret != len) |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1505 return -1; |
3962
72efef66f566
This patch refactors RDT packet header parsing so that it can be used in
rbultje
parents:
3961
diff
changeset
|
1506 if (rt->transport == RTSP_TRANSPORT_RDT && |
4029
9a0a46d465ae
Add is_keyframe param to ff_rdt_parse_header(). See ML discussion in
rbultje
parents:
4026
diff
changeset
|
1507 ff_rdt_parse_header(buf, len, &id, NULL, NULL, NULL, NULL) < 0) |
3962
72efef66f566
This patch refactors RDT packet header parsing so that it can be used in
rbultje
parents:
3961
diff
changeset
|
1508 return -1; |
885 | 1509 |
0 | 1510 /* find the matching stream */ |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1511 for (i = 0; i < rt->nb_rtsp_streams; i++) { |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1512 rtsp_st = rt->rtsp_streams[i]; |
885 | 1513 if (id >= rtsp_st->interleaved_min && |
1514 id <= rtsp_st->interleaved_max) | |
0 | 1515 goto found; |
1516 } | |
1517 goto redo; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1518 found: |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1519 *prtsp_st = rtsp_st; |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1520 return len; |
0 | 1521 } |
1522 | |
5493 | 1523 static int rtsp_fetch_packet(AVFormatContext *s, AVPacket *pkt) |
1524 { | |
1525 RTSPState *rt = s->priv_data; | |
1526 int ret, len; | |
1527 uint8_t buf[10 * RTP_MAX_PACKET_LENGTH]; | |
1528 RTSPStream *rtsp_st; | |
1529 | |
1530 /* get next frames from the same RTP packet */ | |
1531 if (rt->cur_transport_priv) { | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1532 if (rt->transport == RTSP_TRANSPORT_RDT) { |
5493 | 1533 ret = ff_rdt_parse_packet(rt->cur_transport_priv, pkt, NULL, 0); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1534 } else |
5493 | 1535 ret = rtp_parse_packet(rt->cur_transport_priv, pkt, NULL, 0); |
1536 if (ret == 0) { | |
1537 rt->cur_transport_priv = NULL; | |
1538 return 0; | |
1539 } else if (ret == 1) { | |
1540 return 0; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1541 } else |
5493 | 1542 rt->cur_transport_priv = NULL; |
1543 } | |
1544 | |
1545 /* read next RTP packet */ | |
1546 redo: | |
1547 switch(rt->lower_transport) { | |
1548 default: | |
1549 #if CONFIG_RTSP_DEMUXER | |
1550 case RTSP_LOWER_TRANSPORT_TCP: | |
1551 len = tcp_read_packet(s, &rtsp_st, buf, sizeof(buf)); | |
1552 break; | |
1553 #endif | |
1554 case RTSP_LOWER_TRANSPORT_UDP: | |
1555 case RTSP_LOWER_TRANSPORT_UDP_MULTICAST: | |
1556 len = udp_read_packet(s, &rtsp_st, buf, sizeof(buf)); | |
1557 if (len >=0 && rtsp_st->transport_priv && rt->transport == RTSP_TRANSPORT_RTP) | |
1558 rtp_check_and_send_back_rr(rtsp_st->transport_priv, len); | |
1559 break; | |
1560 } | |
1561 if (len < 0) | |
1562 return len; | |
1563 if (len == 0) | |
1564 return AVERROR_EOF; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1565 if (rt->transport == RTSP_TRANSPORT_RDT) { |
5493 | 1566 ret = ff_rdt_parse_packet(rtsp_st->transport_priv, pkt, buf, len); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1567 } else |
5493 | 1568 ret = rtp_parse_packet(rtsp_st->transport_priv, pkt, buf, len); |
1569 if (ret < 0) | |
1570 goto redo; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1571 if (ret == 1) |
5493 | 1572 /* more packets may follow, so we save the RTP context */ |
1573 rt->cur_transport_priv = rtsp_st->transport_priv; | |
1574 | |
1575 return ret; | |
1576 } | |
1577 | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1578 static int rtsp_read_packet(AVFormatContext *s, AVPacket *pkt) |
0 | 1579 { |
1580 RTSPState *rt = s->priv_data; | |
5366
a04be95927ac
Split the sdp_read_packet() function out of rtsp_read_packet().
lucabe
parents:
5365
diff
changeset
|
1581 int ret; |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1582 RTSPMessageHeader reply1, *reply = &reply1; |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1583 char cmd[1024]; |
0 | 1584 |
4166
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1585 if (rt->server_type == RTSP_SERVER_REAL) { |
3903
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1586 int i; |
4166
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1587 enum AVDiscard cache[MAX_STREAMS]; |
3903
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1588 |
4166
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1589 for (i = 0; i < s->nb_streams; i++) |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1590 cache[i] = s->streams[i]->discard; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1591 |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1592 if (!rt->need_subscription) { |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1593 if (memcmp (cache, rt->real_setup_cache, |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1594 sizeof(enum AVDiscard) * s->nb_streams)) { |
5569
346dce85a801
Pretty embarassing bug; we shouldn't use av_strlcatf() on an uninitialized
rbultje
parents:
5529
diff
changeset
|
1595 snprintf(cmd, sizeof(cmd), |
5570 | 1596 "SET_PARAMETER %s RTSP/1.0\r\n" |
1597 "Unsubscribe: %s\r\n", | |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
1598 rt->control_uri, rt->last_subscription); |
4166
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1599 rtsp_send_cmd(s, cmd, reply, NULL); |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1600 if (reply->status_code != RTSP_STATUS_OK) |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1601 return AVERROR_INVALIDDATA; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1602 rt->need_subscription = 1; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1603 } |
3903
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1604 } |
4166
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1605 |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1606 if (rt->need_subscription) { |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1607 int r, rule_nr, first = 1; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1608 |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1609 memcpy(rt->real_setup_cache, cache, |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1610 sizeof(enum AVDiscard) * s->nb_streams); |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1611 rt->last_subscription[0] = 0; |
3903
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1612 |
4166
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1613 snprintf(cmd, sizeof(cmd), |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1614 "SET_PARAMETER %s RTSP/1.0\r\n" |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1615 "Subscribe: ", |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
1616 rt->control_uri); |
4166
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1617 for (i = 0; i < rt->nb_rtsp_streams; i++) { |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1618 rule_nr = 0; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1619 for (r = 0; r < s->nb_streams; r++) { |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1620 if (s->streams[r]->priv_data == rt->rtsp_streams[i]) { |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1621 if (s->streams[r]->discard != AVDISCARD_ALL) { |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1622 if (!first) |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1623 av_strlcat(rt->last_subscription, ",", |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1624 sizeof(rt->last_subscription)); |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1625 ff_rdt_subscribe_rule( |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1626 rt->last_subscription, |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1627 sizeof(rt->last_subscription), i, rule_nr); |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1628 first = 0; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1629 } |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1630 rule_nr++; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1631 } |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1632 } |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1633 } |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1634 av_strlcatf(cmd, sizeof(cmd), "%s\r\n", rt->last_subscription); |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1635 rtsp_send_cmd(s, cmd, reply, NULL); |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1636 if (reply->status_code != RTSP_STATUS_OK) |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1637 return AVERROR_INVALIDDATA; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1638 rt->need_subscription = 0; |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1639 |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1640 if (rt->state == RTSP_STATE_PLAYING) |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1641 rtsp_read_play (s); |
1dbda91eaebd
Allow subscription to any of the streams, not just the first, available in
rbultje
parents:
4165
diff
changeset
|
1642 } |
3903
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1643 } |
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1644 |
5480 | 1645 ret = rtsp_fetch_packet(s, pkt); |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1646 if (ret < 0) |
5366
a04be95927ac
Split the sdp_read_packet() function out of rtsp_read_packet().
lucabe
parents:
5365
diff
changeset
|
1647 return ret; |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1648 |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1649 /* send dummy request to keep TCP connection alive */ |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1650 if ((rt->server_type == RTSP_SERVER_WMS || |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1651 rt->server_type == RTSP_SERVER_REAL) && |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1652 (av_gettime() - rt->last_cmd_time) / 1000000 >= rt->timeout / 2) { |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1653 if (rt->server_type == RTSP_SERVER_WMS) { |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1654 snprintf(cmd, sizeof(cmd) - 1, |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1655 "GET_PARAMETER %s RTSP/1.0\r\n", |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
1656 rt->control_uri); |
5572
820f0889bc45
Remove reply and content_ptr arguments from rtsp_send_cmd_async(), since
rbultje
parents:
5571
diff
changeset
|
1657 rtsp_send_cmd_async(s, cmd); |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1658 } else { |
5572
820f0889bc45
Remove reply and content_ptr arguments from rtsp_send_cmd_async(), since
rbultje
parents:
5571
diff
changeset
|
1659 rtsp_send_cmd_async(s, "OPTIONS * RTSP/1.0\r\n"); |
4877
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1660 } |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1661 } |
940946a4569b
Send dummy requests over the TCP connection (WMS wants GET_PARAMETER,
rbultje
parents:
4875
diff
changeset
|
1662 |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1663 return 0; |
0 | 1664 } |
1665 | |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1666 /* pause the stream */ |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1667 static int rtsp_read_pause(AVFormatContext *s) |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1668 { |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1669 RTSPState *rt = s->priv_data; |
4557
bfe6fb676d46
Rename RTSPHeader to RTSPMessageHeader to reflect more clearly what the
rbultje
parents:
4549
diff
changeset
|
1670 RTSPMessageHeader reply1, *reply = &reply1; |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1671 char cmd[1024]; |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1672 |
179 | 1673 rt = s->priv_data; |
885 | 1674 |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1675 if (rt->state != RTSP_STATE_PLAYING) |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1676 return 0; |
3923
83e51bcb03c2
Rename RTSP_SERVER_RDT to RTSP_SERVER_REAL, because RDT (the transport
rbultje
parents:
3920
diff
changeset
|
1677 else if (!(rt->server_type == RTSP_SERVER_REAL && rt->need_subscription)) { |
3904 | 1678 snprintf(cmd, sizeof(cmd), |
1679 "PAUSE %s RTSP/1.0\r\n", | |
5574
016f3d4fe56d
Use the control URI from the SDP (if present) rather than the input filename,
rbultje
parents:
5572
diff
changeset
|
1680 rt->control_uri); |
3904 | 1681 rtsp_send_cmd(s, cmd, reply, NULL); |
1682 if (reply->status_code != RTSP_STATUS_OK) { | |
1683 return -1; | |
1684 } | |
3903
aeb79f68ba7e
Implement a RDT-specific SET_PARAMETER command that subscribes to the
rbultje
parents:
3877
diff
changeset
|
1685 } |
3861
a0098594ab90
Remove useless "else" case in if X { A; return }; else { B }. See discussion
rbultje
parents:
3860
diff
changeset
|
1686 rt->state = RTSP_STATE_PAUSED; |
a0098594ab90
Remove useless "else" case in if X { A; return }; else { B }. See discussion
rbultje
parents:
3860
diff
changeset
|
1687 return 0; |
179 | 1688 } |
1689 | |
885 | 1690 static int rtsp_read_seek(AVFormatContext *s, int stream_index, |
558 | 1691 int64_t timestamp, int flags) |
179 | 1692 { |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1693 RTSPState *rt = s->priv_data; |
885 | 1694 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1695 rt->seek_timestamp = av_rescale_q(timestamp, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1696 s->streams[stream_index]->time_base, |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1697 AV_TIME_BASE_Q); |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1698 switch(rt->state) { |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1699 default: |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1700 case RTSP_STATE_IDLE: |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1701 break; |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1702 case RTSP_STATE_PLAYING: |
5013 | 1703 if (rtsp_read_pause(s) != 0) |
1704 return -1; | |
1705 rt->state = RTSP_STATE_SEEKING; | |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1706 if (rtsp_read_play(s) != 0) |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1707 return -1; |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1708 break; |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1709 case RTSP_STATE_PAUSED: |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1710 rt->state = RTSP_STATE_IDLE; |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1711 break; |
179 | 1712 } |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1713 return 0; |
179 | 1714 } |
1715 | |
0 | 1716 static int rtsp_read_close(AVFormatContext *s) |
1717 { | |
1718 RTSPState *rt = s->priv_data; | |
1719 char cmd[1024]; | |
1720 | |
172 | 1721 #if 0 |
0 | 1722 /* NOTE: it is valid to flush the buffer here */ |
3957
9f943bb755f9
Rename RTSPProtocol to RTSPLowerTransport, so that its name properly tells us
rbultje
parents:
3941
diff
changeset
|
1723 if (rt->lower_transport == RTSP_LOWER_TRANSPORT_TCP) { |
0 | 1724 url_fclose(&rt->rtsp_gb); |
1725 } | |
172 | 1726 #endif |
885 | 1727 snprintf(cmd, sizeof(cmd), |
172 | 1728 "TEARDOWN %s RTSP/1.0\r\n", |
0 | 1729 s->filename); |
5572
820f0889bc45
Remove reply and content_ptr arguments from rtsp_send_cmd_async(), since
rbultje
parents:
5571
diff
changeset
|
1730 rtsp_send_cmd_async(s, cmd); |
0 | 1731 |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1732 rtsp_close_streams(rt); |
0 | 1733 url_close(rt->rtsp_hd); |
1734 return 0; | |
1735 } | |
1736 | |
1167 | 1737 AVInputFormat rtsp_demuxer = { |
0 | 1738 "rtsp", |
3424
7a0230981402
Make long_names in lavf/lavdev optional depending on CONFIG_SMALL.
diego
parents:
3286
diff
changeset
|
1739 NULL_IF_CONFIG_SMALL("RTSP input format"), |
0 | 1740 sizeof(RTSPState), |
1741 rtsp_probe, | |
1742 rtsp_read_header, | |
1743 rtsp_read_packet, | |
1744 rtsp_read_close, | |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1745 rtsp_read_seek, |
0 | 1746 .flags = AVFMT_NOFILE, |
304
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1747 .read_play = rtsp_read_play, |
d58c8859ff8c
initial seek support - more generic play/pause support
bellard
parents:
294
diff
changeset
|
1748 .read_pause = rtsp_read_pause, |
0 | 1749 }; |
2054 | 1750 #endif |
0 | 1751 |
1752 static int sdp_probe(AVProbeData *p1) | |
1753 { | |
706
fc254f396f15
buffer overflow in sdp_probe() fix by (Gildas Bazin )gbazin altern org)
michael
parents:
587
diff
changeset
|
1754 const char *p = p1->buf, *p_end = p1->buf + p1->buf_size; |
0 | 1755 |
1756 /* we look for a line beginning "c=IN IP4" */ | |
706
fc254f396f15
buffer overflow in sdp_probe() fix by (Gildas Bazin )gbazin altern org)
michael
parents:
587
diff
changeset
|
1757 while (p < p_end && *p != '\0') { |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1758 if (p + sizeof("c=IN IP4") - 1 < p_end && |
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1759 av_strstart(p, "c=IN IP4", NULL)) |
0 | 1760 return AVPROBE_SCORE_MAX / 2; |
706
fc254f396f15
buffer overflow in sdp_probe() fix by (Gildas Bazin )gbazin altern org)
michael
parents:
587
diff
changeset
|
1761 |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1762 while (p < p_end - 1 && *p != '\n') p++; |
706
fc254f396f15
buffer overflow in sdp_probe() fix by (Gildas Bazin )gbazin altern org)
michael
parents:
587
diff
changeset
|
1763 if (++p >= p_end) |
0 | 1764 break; |
1765 if (*p == '\r') | |
1766 p++; | |
1767 } | |
1768 return 0; | |
1769 } | |
1770 | |
1771 #define SDP_MAX_SIZE 8192 | |
1772 | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1773 static int sdp_read_header(AVFormatContext *s, AVFormatParameters *ap) |
0 | 1774 { |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1775 RTSPState *rt = s->priv_data; |
0 | 1776 RTSPStream *rtsp_st; |
1777 int size, i, err; | |
1778 char *content; | |
1779 char url[1024]; | |
1780 | |
1781 /* read the whole sdp file */ | |
1782 /* XXX: better loading */ | |
1783 content = av_malloc(SDP_MAX_SIZE); | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2759
diff
changeset
|
1784 size = get_buffer(s->pb, content, SDP_MAX_SIZE - 1); |
0 | 1785 if (size <= 0) { |
1786 av_free(content); | |
1787 return AVERROR_INVALIDDATA; | |
1788 } | |
1789 content[size] ='\0'; | |
1790 | |
1791 sdp_parse(s, content); | |
1792 av_free(content); | |
1793 | |
1794 /* open each RTP stream */ | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1795 for (i = 0; i < rt->nb_rtsp_streams; i++) { |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1796 rtsp_st = rt->rtsp_streams[i]; |
885 | 1797 |
3222 | 1798 snprintf(url, sizeof(url), "rtp://%s:%d?localport=%d&ttl=%d", |
885 | 1799 inet_ntoa(rtsp_st->sdp_ip), |
0 | 1800 rtsp_st->sdp_port, |
3222 | 1801 rtsp_st->sdp_port, |
0 | 1802 rtsp_st->sdp_ttl); |
1425
00d9393a126f
make ffmpeg able to send back a RTCP receiver report.
gpoirier
parents:
1424
diff
changeset
|
1803 if (url_open(&rtsp_st->rtp_handle, url, URL_RDWR) < 0) { |
0 | 1804 err = AVERROR_INVALIDDATA; |
1805 goto fail; | |
1806 } | |
3919
1879eab34f88
Factorize out common code for opening of the RTP parsing context between
rbultje
parents:
3905
diff
changeset
|
1807 if ((err = rtsp_open_transport_ctx(s, rtsp_st))) |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1808 goto fail; |
0 | 1809 } |
1810 return 0; | |
5502
da007db2fe9c
Re-indent to more closely follow general coding standards used in other
rbultje
parents:
5493
diff
changeset
|
1811 fail: |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1812 rtsp_close_streams(rt); |
0 | 1813 return err; |
1814 } | |
1815 | |
1816 static int sdp_read_close(AVFormatContext *s) | |
1817 { | |
294
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1818 RTSPState *rt = s->priv_data; |
6091b76cfc2a
added MPEG2TS support in RTP, SDP and RTSP - replaced fake RTP demux by a specific API
bellard
parents:
229
diff
changeset
|
1819 rtsp_close_streams(rt); |
0 | 1820 return 0; |
1821 } | |
1822 | |
1169 | 1823 AVInputFormat sdp_demuxer = { |
0 | 1824 "sdp", |
3424
7a0230981402
Make long_names in lavf/lavdev optional depending on CONFIG_SMALL.
diego
parents:
3286
diff
changeset
|
1825 NULL_IF_CONFIG_SMALL("SDP"), |
0 | 1826 sizeof(RTSPState), |
1827 sdp_probe, | |
1828 sdp_read_header, | |
5480 | 1829 rtsp_fetch_packet, |
0 | 1830 sdp_read_close, |
1831 }; |