Skip to content

Commit 9da2d88

Browse files
committed
Merge branch 'master' of github.com:sipsorcery/sipsorcery
2 parents 58a7245 + 92b166e commit 9da2d88

File tree

2 files changed

+87
-31
lines changed

2 files changed

+87
-31
lines changed

src/net/SDP/SDP.cs

+44-31
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
//
99
// History:
1010
// 20 Oct 2005 Aaron Clauson Created.
11+
// rj2: save raw string of SDP, in case there is something in it, that can't be parsed
1112
//
1213
// Notes:
1314
//
@@ -120,6 +121,8 @@ public class SDP
120121

121122
public decimal Version = SDP_PROTOCOL_VERSION;
122123

124+
private string m_rawSdp = null;
125+
123126
// Owner fields.
124127
public string Username = "-"; // Username of the session originator.
125128
public string SessionId = "-"; // Unique Id for the session.
@@ -174,63 +177,65 @@ public static SDP ParseSDPDescription(string sdpDescription)
174177
if (sdpDescription != null && sdpDescription.Trim().Length > 0)
175178
{
176179
SDP sdp = new SDP();
180+
sdp.m_rawSdp = sdpDescription;
177181
SDPMediaAnnouncement activeAnnouncement = null;
178182

179183
string[] sdpLines = Regex.Split(sdpDescription, CRLF);
180184

181185
foreach (string sdpLine in sdpLines)
182186
{
183-
if (sdpLine.Trim().StartsWith("v="))
187+
string sdpLineTrimmed = sdpLine.Trim();
188+
if (sdpLineTrimmed.StartsWith("v="))
184189
{
185-
if (!Decimal.TryParse(sdpLine.Substring(2), out sdp.Version))
190+
if (!Decimal.TryParse(sdpLineTrimmed.Substring(2), out sdp.Version))
186191
{
187192
logger.LogWarning("The Version value in an SDP description could not be parsed as a decimal: " + sdpLine + ".");
188193
}
189194
}
190-
else if (sdpLine.Trim().StartsWith("o="))
195+
else if (sdpLineTrimmed.StartsWith("o="))
191196
{
192-
string[] ownerFields = sdpLine.Substring(2).Split(' ');
197+
string[] ownerFields = sdpLineTrimmed.Substring(2).Split(' ');
193198
sdp.Username = ownerFields[0];
194199
sdp.SessionId = ownerFields[1];
195200
Int32.TryParse(ownerFields[2], out sdp.AnnouncementVersion);
196201
sdp.NetworkType = ownerFields[3];
197202
sdp.AddressType = ownerFields[4];
198203
sdp.Address = ownerFields[5];
199204
}
200-
else if (sdpLine.Trim().StartsWith("s="))
205+
else if (sdpLineTrimmed.StartsWith("s="))
201206
{
202-
sdp.SessionName = sdpLine.Substring(2);
207+
sdp.SessionName = sdpLineTrimmed.Substring(2);
203208
}
204-
else if (sdpLine.Trim().StartsWith("c="))
209+
else if (sdpLineTrimmed.StartsWith("c="))
205210
{
206211
if (sdp.Connection == null)
207212
{
208-
sdp.Connection = SDPConnectionInformation.ParseConnectionInformation(sdpLine);
213+
sdp.Connection = SDPConnectionInformation.ParseConnectionInformation(sdpLineTrimmed);
209214
}
210215

211216
if (activeAnnouncement != null)
212217
{
213-
activeAnnouncement.Connection = SDPConnectionInformation.ParseConnectionInformation(sdpLine);
218+
activeAnnouncement.Connection = SDPConnectionInformation.ParseConnectionInformation(sdpLineTrimmed);
214219
}
215220
}
216-
else if (sdpLine.Trim().StartsWith("b="))
221+
else if (sdpLineTrimmed.StartsWith("b="))
217222
{
218223
if (activeAnnouncement != null)
219224
{
220-
activeAnnouncement.BandwidthAttributes.Add(sdpLine.Substring(2));
225+
activeAnnouncement.BandwidthAttributes.Add(sdpLineTrimmed.Substring(2));
221226
}
222227
else
223228
{
224-
sdp.BandwidthAttributes.Add(sdpLine.Substring(2));
229+
sdp.BandwidthAttributes.Add(sdpLineTrimmed.Substring(2));
225230
}
226231
}
227-
else if (sdpLine.Trim().StartsWith("t="))
232+
else if (sdpLineTrimmed.StartsWith("t="))
228233
{
229-
sdp.Timing = sdpLine.Substring(2);
234+
sdp.Timing = sdpLineTrimmed.Substring(2);
230235
}
231-
else if (sdpLine.Trim().StartsWith("m="))
236+
else if (sdpLineTrimmed.StartsWith("m="))
232237
{
233-
Match mediaMatch = Regex.Match(sdpLine.Substring(2).Trim(), @"(?<type>\w+)\s+(?<port>\d+)\s+(?<transport>\S+)(\s*)(?<formats>.*)$");
238+
Match mediaMatch = Regex.Match(sdpLineTrimmed.Substring(2), @"(?<type>\w+)\s+(?<port>\d+)\s+(?<transport>\S+)(\s*)(?<formats>.*)$");
234239
if (mediaMatch.Success)
235240
{
236241
SDPMediaAnnouncement announcement = new SDPMediaAnnouncement();
@@ -244,22 +249,22 @@ public static SDP ParseSDPDescription(string sdpDescription)
244249
}
245250
else
246251
{
247-
logger.LogWarning("A media line in SDP was invalid: " + sdpLine.Substring(2) + ".");
252+
logger.LogWarning("A media line in SDP was invalid: " + sdpLineTrimmed.Substring(2) + ".");
248253
}
249254
}
250-
else if (sdpLine.Trim().StartsWith("a=" + ICE_UFRAG_ATTRIBUTE_PREFIX))
255+
else if (sdpLineTrimmed.StartsWith("a=" + ICE_UFRAG_ATTRIBUTE_PREFIX))
251256
{
252-
sdp.IceUfrag = sdpLine.Substring(sdpLine.IndexOf(':') + 1);
257+
sdp.IceUfrag = sdpLineTrimmed.Substring(sdpLineTrimmed.IndexOf(':') + 1);
253258
}
254-
else if (sdpLine.Trim().StartsWith("a=" + ICE_PWD_ATTRIBUTE_PREFIX))
259+
else if (sdpLineTrimmed.StartsWith("a=" + ICE_PWD_ATTRIBUTE_PREFIX))
255260
{
256-
sdp.IcePwd = sdpLine.Substring(sdpLine.IndexOf(':') + 1);
261+
sdp.IcePwd = sdpLineTrimmed.Substring(sdpLineTrimmed.IndexOf(':') + 1);
257262
}
258-
else if (sdpLine.Trim().StartsWith(SDPMediaAnnouncement.MEDIA_FORMAT_ATTRIBUE_PREFIX))
263+
else if (sdpLineTrimmed.StartsWith(SDPMediaAnnouncement.MEDIA_FORMAT_ATTRIBUE_PREFIX))
259264
{
260265
if (activeAnnouncement != null)
261266
{
262-
Match formatAttributeMatch = Regex.Match(sdpLine.Trim(), SDPMediaAnnouncement.MEDIA_FORMAT_ATTRIBUE_PREFIX + @"(?<id>\d+)\s+(?<attribute>.*)$");
267+
Match formatAttributeMatch = Regex.Match(sdpLineTrimmed, SDPMediaAnnouncement.MEDIA_FORMAT_ATTRIBUE_PREFIX + @"(?<id>\d+)\s+(?<attribute>.*)$");
263268
if (formatAttributeMatch.Success)
264269
{
265270
int formatID;
@@ -274,19 +279,19 @@ public static SDP ParseSDPDescription(string sdpDescription)
274279
}
275280
else
276281
{
277-
activeAnnouncement.AddExtra(sdpLine);
282+
activeAnnouncement.AddExtra(sdpLineTrimmed);
278283
}
279284
}
280285
else
281286
{
282287
logger.LogWarning("There was no active media announcement for a media format attribute, ignoring.");
283288
}
284289
}
285-
else if (sdpLine.Trim().StartsWith(SDPMediaAnnouncement.MEDIA_FORMAT_PARAMETERS_ATTRIBUE_PREFIX))
290+
else if (sdpLineTrimmed.StartsWith(SDPMediaAnnouncement.MEDIA_FORMAT_PARAMETERS_ATTRIBUE_PREFIX))
286291
{
287292
if (activeAnnouncement != null)
288293
{
289-
Match formatAttributeMatch = Regex.Match(sdpLine.Trim(), SDPMediaAnnouncement.MEDIA_FORMAT_PARAMETERS_ATTRIBUE_PREFIX + @"(?<id>\d+)\s+(?<attribute>.*)$");
294+
Match formatAttributeMatch = Regex.Match(sdpLineTrimmed, SDPMediaAnnouncement.MEDIA_FORMAT_PARAMETERS_ATTRIBUE_PREFIX + @"(?<id>\d+)\s+(?<attribute>.*)$");
290295
if (formatAttributeMatch.Success)
291296
{
292297
int formatID;
@@ -301,22 +306,22 @@ public static SDP ParseSDPDescription(string sdpDescription)
301306
}
302307
else
303308
{
304-
activeAnnouncement.AddExtra(sdpLine);
309+
activeAnnouncement.AddExtra(sdpLineTrimmed);
305310
}
306311
}
307312
else
308313
{
309314
logger.LogWarning("There was no active media announcement for a media format parameter attribute, ignoring.");
310315
}
311316
}
312-
else if (sdpLine.Trim().StartsWith("a=" + ICE_CANDIDATE_ATTRIBUTE_PREFIX))
317+
else if (sdpLineTrimmed.StartsWith("a=" + ICE_CANDIDATE_ATTRIBUTE_PREFIX))
313318
{
314319
if (sdp.IceCandidates == null)
315320
{
316321
sdp.IceCandidates = new List<IceCandidate>();
317322
}
318323

319-
sdp.IceCandidates.Add(IceCandidate.Parse(sdpLine.Substring(sdpLine.IndexOf(':') + 1)));
324+
sdp.IceCandidates.Add(IceCandidate.Parse(sdpLineTrimmed.Substring(sdpLineTrimmed.IndexOf(':') + 1)));
320325
}
321326
else if (MediaStreamStatusType.IsMediaStreamStatusAttribute(sdpLine.Trim(), out var mediaStreamStatus))
322327
{
@@ -333,11 +338,11 @@ public static SDP ParseSDPDescription(string sdpDescription)
333338
{
334339
if (activeAnnouncement != null)
335340
{
336-
activeAnnouncement.AddExtra(sdpLine);
341+
activeAnnouncement.AddExtra(sdpLineTrimmed);
337342
}
338343
else
339344
{
340-
sdp.AddExtra(sdpLine);
345+
sdp.AddExtra(sdpLineTrimmed);
341346
}
342347
}
343348
}
@@ -364,6 +369,14 @@ public void AddExtra(string attribute)
364369
}
365370
}
366371

372+
public string RawString()
373+
{
374+
if (string.IsNullOrWhiteSpace(this.m_rawSdp))
375+
{
376+
return this.ToString();
377+
}
378+
return this.m_rawSdp;
379+
}
367380
public override string ToString()
368381
{
369382
string sdp =

test/net/SDPUnitTests.cs

+43
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,49 @@ public void ParseBriaSDPUnitTest()
7474
Assert.True(sdp.Media[0].MediaFormats[0].Name == "PCMU", "The highest priority media format name was incorrect.");
7575
}
7676

77+
[Fact]
78+
public void ParseBadFormatSDPUnitTest()
79+
{
80+
Console.WriteLine(System.Reflection.MethodBase.GetCurrentMethod().Name);
81+
82+
string sdpStr =
83+
" v=0" + m_CRLF +
84+
" o=root 3285 3285 IN IP4 10.0.0.4" + m_CRLF +
85+
" s=session" + m_CRLF +
86+
" c=IN IP4 10.0.0.4" + m_CRLF +
87+
" t=0 0" + m_CRLF +
88+
" m=audio 12228 RTP/AVP 0 101" + m_CRLF +
89+
" a=rtpmap:0 PCMU/8000" + m_CRLF +
90+
" a=rtpmap:101 telephone-event/8000" + m_CRLF +
91+
" a=fmtp:101 0-16" + m_CRLF +
92+
" a=silenceSupp:off - - - -" + m_CRLF +
93+
" a=ptime:20" + m_CRLF +
94+
" a=sendrecv";
95+
96+
SDP sdp = SDP.ParseSDPDescription(sdpStr);
97+
98+
Debug.WriteLine(sdp.ToString());
99+
100+
Assert.True(sdp.Connection.ConnectionAddress == "10.0.0.4", "The connection address was not parsed correctly.");
101+
Assert.True(sdp.Username == "root", "The owner was not parsed correctly.");
102+
Assert.True(sdp.SessionName == "session", "The SessionName was not parsed correctly.");
103+
Assert.True(sdp.Media[0].Media == SDPMediaTypesEnum.audio, "The media type not parsed correctly.");
104+
}
105+
106+
[Fact]
107+
public void ParseBadFormatBriaSDPUnitTest()
108+
{
109+
Console.WriteLine(System.Reflection.MethodBase.GetCurrentMethod().Name);
110+
string sdpStr = " v=0\r\no=- 5 2 IN IP4 10.1.1.2\r\n s=CounterPath Bria\r\nc=IN IP4 144.137.16.240\r\nt=0 0\r\n m=audio 34640 RTP/AVP 0 8 101\r\na=sendrecv\r\na=rtpmap:101 telephone-event/8000\r\na=fmtp:101 0-15\r\na=alt:1 1 : STu/ZtOu 7hiLQmUp 10.1.1.2 34640\r\n";
111+
112+
SDP sdp = SDP.ParseSDPDescription(sdpStr);
113+
114+
Debug.WriteLine(sdp.ToString());
115+
116+
Assert.True(sdp.Connection.ConnectionAddress == "144.137.16.240", "The connection address was not parsed correctly.");
117+
Assert.True(sdp.SessionName == "CounterPath Bria", "The SessionName was not parsed correctly.");
118+
}
119+
77120
[Fact]
78121
public void ParseICESessionAttributesUnitTest()
79122
{

0 commit comments

Comments
 (0)