srs_rtsp_stack.hpp
9.7 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
/*
The MIT License (MIT)
Copyright (c) 2013-2015 winlin
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
#ifndef SRS_PROTOCOL_RTSP_STACK_HPP
#define SRS_PROTOCOL_RTSP_STACK_HPP
/*
#include <srs_rtsp_stack.hpp>
*/
#include <srs_core.hpp>
#include <string>
#include <sstream>
#include <srs_kernel_consts.hpp>
#ifdef SRS_AUTO_STREAM_CASTER
class SrsSimpleBuffer;
class ISrsProtocolReaderWriter;
// rtsp specification
// CR = <US-ASCII CR, carriage return (13)>
#define __SRS_RTSP_CR SRS_CONSTS_CR // 0x0D
// LF = <US-ASCII LF, linefeed (10)>
#define __SRS_RTSP_LF SRS_CONSTS_LF // 0x0A
// SP = <US-ASCII SP, space (32)>
#define __SRS_RTSP_SP ' ' // 0x20
// 4 RTSP Message
// Lines are terminated by CRLF, but
// receivers should be prepared to also interpret CR and LF by
// themselves as line terminators.
#define __SRS_RTSP_CRLF "\r\n" // 0x0D0A
#define __SRS_RTSP_CRLFCRLF "\r\n\r\n" // 0x0D0A0D0A
// RTSP token
#define __SRS_TOKEN_CSEQ "CSeq"
#define __SRS_TOKEN_PUBLIC "Public"
// RTSP methods
#define __SRS_METHOD_OPTIONS "OPTIONS"
#define __SRS_METHOD_DESCRIBE "DESCRIBE"
#define __SRS_METHOD_ANNOUNCE "ANNOUNCE"
#define __SRS_METHOD_SETUP "SETUP"
#define __SRS_METHOD_PLAY "PLAY"
#define __SRS_METHOD_PAUSE "PAUSE"
#define __SRS_METHOD_TEARDOWN "TEARDOWN"
#define __SRS_METHOD_GET_PARAMETER "GET_PARAMETER"
#define __SRS_METHOD_SET_PARAMETER "SET_PARAMETER"
#define __SRS_METHOD_REDIRECT "REDIRECT"
#define __SRS_METHOD_RECORD "RECORD"
// Embedded (Interleaved) Binary Data
// RTSP-Version
#define __SRS_VERSION "RTSP/1.0"
/**
* the rtsp request message.
* 6 Request
* A request message from a client to a server or vice versa includes,
* within the first line of that message, the method to be applied to
* the resource, the identifier of the resource, and the protocol
* version in use.
* Request = Request-Line ; Section 6.1
* *( general-header ; Section 5
* | request-header ; Section 6.2
* | entity-header ) ; Section 8.1
* CRLF
* [ message-body ] ; Section 4.3
*/
class SrsRtspRequest
{
public:
/**
* 6.1 Request Line
* Request-Line = Method SP Request-URI SP RTSP-Version CRLF
*/
std::string method;
std::string uri;
std::string version;
/**
* 12.17 CSeq
* The CSeq field specifies the sequence number for an RTSP requestresponse
* pair. This field MUST be present in all requests and
* responses. For every RTSP request containing the given sequence
* number, there will be a corresponding response having the same
* number. Any retransmitted request must contain the same sequence
* number as the original (i.e. the sequence number is not incremented
* for retransmissions of the same request).
*/
int seq;
public:
SrsRtspRequest();
virtual ~SrsRtspRequest();
public:
virtual bool is_options();
};
/**
* the rtsp response message.
* 7 Response
* [H6] applies except that HTTP-Version is replaced by RTSP-Version.
* Also, RTSP defines additional status codes and does not define some
* HTTP codes. The valid response codes and the methods they can be used
* with are defined in Table 1.
* After receiving and interpreting a request message, the recipient
* responds with an RTSP response message.
* Response = Status-Line ; Section 7.1
* *( general-header ; Section 5
* | response-header ; Section 7.1.2
* | entity-header ) ; Section 8.1
* CRLF
* [ message-body ] ; Section 4.3
*/
class SrsRtspResponse
{
public:
/**
* 7.1 Status-Line
* The first line of a Response message is the Status-Line, consisting
* of the protocol version followed by a numeric status code, and the
* textual phrase associated with the status code, with each element
* separated by SP characters. No CR or LF is allowed except in the
* final CRLF sequence.
* Status-Line = RTSP-Version SP Status-Code SP Reason-Phrase CRLF
*/
// @see about the version of rtsp, see __SRS_VERSION
// @see about the status of rtsp, see SRS_CONSTS_RTSP_OK
int status;
/**
* 12.17 CSeq
* The CSeq field specifies the sequence number for an RTSP requestresponse
* pair. This field MUST be present in all requests and
* responses. For every RTSP request containing the given sequence
* number, there will be a corresponding response having the same
* number. Any retransmitted request must contain the same sequence
* number as the original (i.e. the sequence number is not incremented
* for retransmissions of the same request).
*/
int seq;
public:
SrsRtspResponse(int cseq);
virtual ~SrsRtspResponse();
public:
/**
* encode message to string.
*/
virtual std::stringstream& encode(std::stringstream& ss);
};
/**
* 10 Method Definitions
* The method token indicates the method to be performed on the resource
* identified by the Request-URI. The method is case-sensitive. New
* methods may be defined in the future. Method names may not start with
* a $ character (decimal 24) and must be a token. Methods are
* summarized in Table 2.
* Notes on Table 2: PAUSE is recommended, but not required in that a
* fully functional server can be built that does not support this
* method, for example, for live feeds. If a server does not support a
* particular method, it MUST return "501 Not Implemented" and a client
* SHOULD not try this method again for this server.
*/
enum SrsRtspMethod
{
SrsRtspMethodDescribe = 0x0001,
SrsRtspMethodAnnounce = 0x0002,
SrsRtspMethodGetParameter = 0x0004,
SrsRtspMethodOptions = 0x0008,
SrsRtspMethodPause = 0x0010,
SrsRtspMethodPlay = 0x0020,
SrsRtspMethodRecord = 0x0040,
SrsRtspMethodRedirect = 0x0080,
SrsRtspMethodSetup = 0x0100,
SrsRtspMethodSetParameter = 0x0200,
SrsRtspMethodTeardown = 0x0400,
};
/**
* 10.1 OPTIONS
* The behavior is equivalent to that described in [H9.2]. An OPTIONS
* request may be issued at any time, e.g., if the client is about to
* try a nonstandard request. It does not influence server state.
*/
class SrsRtspOptionsResponse : public SrsRtspResponse
{
public:
/**
* join of SrsRtspMethod
*/
SrsRtspMethod methods;
public:
SrsRtspOptionsResponse(int cseq);
virtual ~SrsRtspOptionsResponse();
public:
virtual std::stringstream& encode(std::stringstream& ss);
};
/**
* the state of rtsp token.
*/
enum SrsRtspTokenState
{
/**
* parse token failed, default state.
*/
SrsRtspTokenStateError = 100,
/**
* when SP follow the token.
*/
SrsRtspTokenStateNormal = 101,
/**
* when CRLF follow the token.
*/
SrsRtspTokenStateEOF = 102,
};
/**
* the rtsp protocol stack to parse the rtsp packets.
*/
class SrsRtspStack
{
private:
/**
* cached bytes buffer.
*/
SrsSimpleBuffer* buf;
/**
* underlayer socket object, send/recv bytes.
*/
ISrsProtocolReaderWriter* skt;
public:
SrsRtspStack(ISrsProtocolReaderWriter* s);
virtual ~SrsRtspStack();
public:
/**
* recv rtsp message from underlayer io.
* @param preq the output rtsp request message, which user must free it.
* @return an int error code.
* ERROR_RTSP_REQUEST_HEADER_EOF indicates request header EOF.
*/
virtual int recv_message(SrsRtspRequest** preq);
/**
* send rtsp message over underlayer io.
* @param res the rtsp response message, which user should never free it.
* @return an int error code.
*/
virtual int send_message(SrsRtspResponse* res);
private:
/**
* recv the rtsp message.
*/
virtual int do_recv_message(SrsRtspRequest* req);
/**
* read a normal token from io, error when token state is not normal.
*/
virtual int recv_token_normal(std::string& token);
/**
* read a normal token from io, error when token state is not eof.
*/
virtual int recv_token_eof(std::string& token);
/**
* read the token util got eof, for example, to read the response status Reason-Phrase
*/
virtual int recv_token_util_eof(std::string& token);
/**
* read a token from io, split by SP, endswith CRLF:
* token1 SP token2 SP ... tokenN CRLF
* @param normal_ch, the char to indicates the normal token.
* the SP use to indicates the normal token, @see __SRS_RTSP_SP
* the 0x00 use to ignore normal token flag. @see recv_token_util_eof
* @param token, output the read token.
* @param state, output the token parse state.
*/
virtual int recv_token(std::string& token, SrsRtspTokenState& state, char normal_ch = __SRS_RTSP_SP);
};
#endif
#endif