1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package io.netty.handler.codec.rtsp;
17
18 import java.util.regex.Pattern;
19
20 import io.netty.buffer.Unpooled;
21 import io.netty.handler.codec.http.DefaultFullHttpRequest;
22 import io.netty.handler.codec.http.DefaultFullHttpResponse;
23 import io.netty.handler.codec.http.DefaultHttpRequest;
24 import io.netty.handler.codec.http.DefaultHttpResponse;
25 import io.netty.handler.codec.http.HttpMessage;
26 import io.netty.handler.codec.http.HttpObjectDecoder;
27 import io.netty.handler.codec.http.HttpResponseStatus;
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 public class RtspDecoder extends HttpObjectDecoder {
59
60
61
62 private static final HttpResponseStatus UNKNOWN_STATUS =
63 new HttpResponseStatus(999, "Unknown");
64
65
66
67
68 private boolean isDecodingRequest;
69
70
71
72
73 private static final Pattern versionPattern = Pattern.compile("RTSP/\\d\\.\\d");
74
75
76
77
78 public static final int DEFAULT_MAX_INITIAL_LINE_LENGTH = 4096;
79
80
81
82
83 public static final int DEFAULT_MAX_HEADER_SIZE = 8192;
84
85
86
87
88 public static final int DEFAULT_MAX_CONTENT_LENGTH = 8192;
89
90
91
92
93
94
95 public RtspDecoder() {
96 this(DEFAULT_MAX_INITIAL_LINE_LENGTH,
97 DEFAULT_MAX_HEADER_SIZE,
98 DEFAULT_MAX_CONTENT_LENGTH);
99 }
100
101
102
103
104
105
106
107 public RtspDecoder(final int maxInitialLineLength,
108 final int maxHeaderSize,
109 final int maxContentLength) {
110 super(maxInitialLineLength, maxHeaderSize, maxContentLength * 2, false);
111 }
112
113
114
115
116
117
118
119
120 public RtspDecoder(final int maxInitialLineLength,
121 final int maxHeaderSize,
122 final int maxContentLength,
123 final boolean validateHeaders) {
124 super(maxInitialLineLength,
125 maxHeaderSize,
126 maxContentLength * 2,
127 false,
128 validateHeaders);
129 }
130
131 @Override
132 protected HttpMessage createMessage(final String[] initialLine)
133 throws Exception {
134
135
136 if (versionPattern.matcher(initialLine[0]).matches()) {
137 isDecodingRequest = false;
138 return new DefaultHttpResponse(RtspVersions.valueOf(initialLine[0]),
139 new HttpResponseStatus(Integer.parseInt(initialLine[1]),
140 initialLine[2]),
141 validateHeaders);
142 } else {
143 isDecodingRequest = true;
144 return new DefaultHttpRequest(RtspVersions.valueOf(initialLine[2]),
145 RtspMethods.valueOf(initialLine[0]),
146 initialLine[1],
147 validateHeaders);
148 }
149 }
150
151 @Override
152 protected boolean isContentAlwaysEmpty(final HttpMessage msg) {
153
154
155 return super.isContentAlwaysEmpty(msg) || !msg.headers().contains(RtspHeaders.Names.CONTENT_LENGTH);
156 }
157
158 @Override
159 protected HttpMessage createInvalidMessage() {
160 if (isDecodingRequest) {
161 return new DefaultFullHttpRequest(RtspVersions.RTSP_1_0,
162 RtspMethods.OPTIONS, "/bad-request", Unpooled.EMPTY_BUFFER, validateHeaders);
163 } else {
164 return new DefaultFullHttpResponse(RtspVersions.RTSP_1_0,
165 UNKNOWN_STATUS, Unpooled.EMPTY_BUFFER,
166 validateHeaders);
167 }
168 }
169
170 @Override
171 protected boolean isDecodingRequest() {
172 return isDecodingRequest;
173 }
174 }