1
/* $Id: msg_test.c 3553 2011-05-05 06:14:19Z nanang $ */
3
* Copyright (C) 2008-2011 Teluu Inc. (http://www.teluu.com)
4
* Copyright (C) 2003-2008 Benny Prijono <benny@prijono.org>
6
* This program is free software; you can redistribute it and/or modify
7
* it under the terms of the GNU General Public License as published by
8
* the Free Software Foundation; either version 2 of the License, or
9
* (at your option) any later version.
11
* This program is distributed in the hope that it will be useful,
12
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14
* GNU General Public License for more details.
16
* You should have received a copy of the GNU General Public License
17
* along with this program; if not, write to the Free Software
18
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24
#define POOL_SIZE 8000
25
#if defined(PJ_DEBUG) && PJ_DEBUG!=0
30
#define AVERAGE_MSG_LEN 800
31
#define THIS_FILE "msg_test.c"
33
static pjsip_msg *create_msg0(pj_pool_t *pool);
34
static pjsip_msg *create_msg1(pj_pool_t *pool);
36
#define STATUS_PARTIAL 1
37
#define STATUS_SYNTAX_ERROR 2
39
#define FLAG_DETECT_ONLY 1
40
#define FLAG_PARSE_ONLY 4
41
#define FLAG_PRINT_ONLY 8
46
pjsip_msg *(*creator)(pj_pool_t *pool);
52
/* 'Normal' message with all headers. */
53
"INVITE sip:user@foo SIP/2.0\n"
54
"from: Hi I'm Joe <sip:joe.user@bar.otherdomain.com>;tag=123457890123456\r"
55
"To: Fellow User <sip:user@foo.bar.domain.com>\r\n"
56
"Call-ID: 12345678901234567890@bar\r\n"
57
"Content-Length: 0\r\n"
58
"CSeq: 123456 INVITE\n"
59
"Contact: <sip:joe@bar> ; q=0.5;expires=3600,sip:user@host;q=0.500\r"
61
"Content-Type: text/html ; charset=ISO-8859-4\r"
62
"Route: <sip:bigbox3.site3.atlanta.com;lr>,\r\n"
63
" <sip:server10.biloxi.com;lr>\r"
64
"Record-Route: <sip:server10.biloxi.com>,\r\n" /* multiple routes+folding*/
65
" <sip:bigbox3.site3.atlanta.com;lr>\n"
66
"v: SIP/2.0/SCTP bigbox3.site3.atlanta.com;branch=z9hG4bK77ef4c230\n"
67
"Via: SIP/2.0/UDP pc33.atlanta.com;branch=z9hG4bKnashds8\n" /* folding. */
68
" ;received=192.0.2.1\r\n"
69
"Via: SIP/2.0/UDP 10.2.1.1, SIP/2.0/TCP 192.168.1.1\n"
72
"X-Header: \r\n" /* empty header */
73
"P-Associated-URI:\r\n" /* empty header without space */
80
/* Typical response message. */
82
"Via: SIP/2.0/SCTP server10.biloxi.com;branch=z9hG4bKnashds8;rport;received=192.0.2.1\r\n"
83
"Via: SIP/2.0/UDP bigbox3.site3.atlanta.com;branch=z9hG4bK77ef4c2312983.1;received=192.0.2.2\r\n"
84
"Via: SIP/2.0/UDP pc33.atlanta.com;branch=z9hG4bK776asdhds ;received=192.0.2.3\r\n"
85
"Route: <sip:proxy.sipprovider.com>\r\n"
86
"Route: <sip:proxy.supersip.com:5060>\r\n"
87
"Max-Forwards: 70\r\n"
88
"To: Bob <sip:bob@biloxi.com>;tag=a6c85cf\r\n"
89
"From: Alice <sip:alice@atlanta.com>;tag=1928301774\r\n"
90
"Call-ID: a84b4c76e66710@pc33.atlanta.com\r\n"
91
"CSeq: 314159 INVITE\r\n"
92
"Contact: <sips:bob@192.0.2.4>\r\n"
93
"Content-Type: application/sdp\r\n"
94
"Content-Length: 150\r\n"
97
"o=alice 53655765 2353687637 IN IP4 pc33.atlanta.com\r\n"
100
"c=IN IP4 pc33.atlanta.com\r\n"
101
"m=audio 3456 RTP/AVP 0 1 3 99\r\n"
102
"a=rtpmap:0 PCMU/8000\r\n",
108
/* Torture message from RFC 4475
109
* 3.1.1.1 A short tortuous INVITE
111
"INVITE sip:vivekg@chair-dnrc.example.com;unknownparam SIP/2.0\n"
113
" sip:vivekg@chair-dnrc.example.com ; tag = 1918181833n\n"
114
"from : \"J Rosenberg \\\\\\\"\" <sip:jdrosen@example.com>\n"
117
"MaX-fOrWaRdS: 0068\n"
118
"Call-ID: wsinv.ndaksdj@192.0.2.1\n"
119
"Content-Length : 150\n"
124
" 192.0.2.2;rport;branch=390skdjuw\n"
126
"NewFangledHeader: newfangled value\n"
127
" continued newfangled value\n"
128
"UnknownHeaderWithUnusualValue: ;;,,;;,;\n"
129
"Content-Type: application/sdp\n"
131
" <sip:services.example.com;lr;unknownwith=value;unknown-no-value>\n"
132
"v: SIP / 2.0 / TCP spindle.example.com ;\n"
133
" branch = z9hG4bK9ikj8 ,\n"
134
" SIP / 2.0 / UDP 192.168.255.111 ; branch=\n"
136
"m:\"Quoted string \\\"\\\"\" <sip:jdrosen@example.com> ; newparam =\n"
138
" secondparam ; q = 0.33\r\n"
141
"o=mhandley 29739 7272939 IN IP4 192.0.2.3\r\n"
143
"c=IN IP4 192.0.2.4\r\n"
145
"m=audio 49217 RTP/AVP 0 12\r\n"
146
"m=video 3227 RTP/AVP 31\r\n"
147
"a=rtpmap:31 LPC\r\n",
153
/* Torture message from RFC 4475
154
* 3.1.1.2 Wide Range of Valid Characters
156
"!interesting-Method0123456789_*+`.%indeed'~ sip:1_unusual.URI~(to-be!sure)&isn't+it$/crazy?,/;;*:&it+has=1,weird!*pas$wo~d_too.(doesn't-it)@example.com SIP/2.0\n"
157
"Via: SIP/2.0/UDP host1.example.com;rport;branch=z9hG4bK-.!%66*_+`'~\n"
158
"To: \"BEL:\\\x07 NUL:\\\x00 DEL:\\\x7F\" <sip:1_unusual.URI~(to-be!sure)&isn't+it$/crazy?,/;;*@example.com>\n"
159
"From: token1~` token2'+_ token3*%!.- <sip:mundane@example.com> ;fromParam''~+*_!.-%=\"\xD1\x80\xD0\xB0\xD0\xB1\xD0\xBE\xD1\x82\xD0\xB0\xD1\x8E\xD1\x89\xD0\xB8\xD0\xB9\";tag=_token~1'+`*%!-.\n"
160
"Call-ID: intmeth.word%ZK-!.*_+'@word`~)(><:\\/\"][?}{\n"
161
"CSeq: 139122385 !interesting-Method0123456789_*+`.%indeed'~\n"
162
"Max-Forwards: 255\n"
163
"extensionHeader-!.%*+_`'~: \xEF\xBB\xBF\xE5\xA4\xA7\xE5\x81\x9C\xE9\x9B\xBB\n"
164
"Content-Length: 0\r\n\r\n",
170
/* Torture message from RFC 4475
171
* 3.1.1.3 Valid Use of the % Escaping Mechanism
173
"INVITE sip:sips%3Auser%40example.com@example.net SIP/2.0\n"
174
"To: sip:%75se%72@example.com\n"
175
"From: <sip:I%20have%20spaces@example.net>;tag=1234\n"
177
"i: esc01.239409asdfakjkn23onasd0-3234\n"
178
"CSeq: 234234 INVITE\n"
179
"Via: SIP/2.0/UDP host5.example.net;rport;branch=z9hG4bKkdjuw\n"
180
"C: application/sdp\n"
182
" <sip:cal%6Cer@192.168.0.2:5060;%6C%72;n%61me=v%61lue%25%34%31>\n"
183
"Content-Length: 150\r\n"
186
"o=mhandley 29739 7272939 IN IP4 192.0.2.1\r\n"
188
"c=IN IP4 192.0.2.1\r\n"
190
"m=audio 49217 RTP/AVP 0 12\r\n"
191
"m=video 3227 RTP/AVP 31\r\n"
192
"a=rtpmap:31 LPC\r\n",
198
/* Torture message from RFC 4475
199
* 3.1.1.4 Escaped Nulls in URIs
201
"REGISTER sip:example.com SIP/2.0\r\n"
202
"To: sip:null-%00-null@example.com\r\n"
203
"From: sip:null-%00-null@example.com;tag=839923423\r\n"
204
"Max-Forwards: 70\r\n"
205
"Call-ID: escnull.39203ndfvkjdasfkq3w4otrq0adsfdfnavd\r\n"
206
"CSeq: 14398234 REGISTER\r\n"
207
"Via: SIP/2.0/UDP host5.example.com;rport;branch=z9hG4bKkdjuw\r\n"
208
"Contact: <sip:%00@host5.example.com>\r\n"
209
"Contact: <sip:%00%00@host5.example.com>\r\n"
217
/* Torture message from RFC 4475
218
* 3.1.1.5 Use of % When It Is Not an Escape
220
"RE%47IST%45R sip:registrar.example.com SIP/2.0\r\n"
221
"To: \"%Z%45\" <sip:resource@example.com>\r\n"
222
"From: \"%Z%45\" <sip:resource@example.com>;tag=f232jadfj23\r\n"
223
"Call-ID: esc02.asdfnqwo34rq23i34jrjasdcnl23nrlknsdf\r\n"
224
"Via: SIP/2.0/TCP host.example.com;rport;branch=z9hG4bK209%fzsnel234\r\n"
225
"CSeq: 29344 RE%47IST%45R\r\n"
226
"Max-Forwards: 70\r\n"
227
"Contact: <sip:alias1@host1.example.com>\r\n"
228
"C%6Fntact: <sip:alias2@host2.example.com>\r\n"
229
"Contact: <sip:alias3@host3.example.com>\r\n"
241
pj_highprec_t detect_len, parse_len, print_len;
242
pj_timestamp detect_time, parse_time, print_time;
245
static pj_status_t test_entry( pj_pool_t *pool, struct test_msg *entry )
247
pjsip_msg *parsed_msg, *ref_msg = NULL;
248
static pjsip_msg *print_msg;
249
pj_status_t status = PJ_SUCCESS;
252
pjsip_hdr *hdr1, *hdr2;
254
pjsip_parser_err_report err_list;
256
char msgbuf1[PJSIP_MAX_PKT_LEN];
257
char msgbuf2[PJSIP_MAX_PKT_LEN];
258
enum { BUFLEN = 512 };
261
entry->len = pj_ansi_strlen(entry->msg);
263
if (var.flag & FLAG_PARSE_ONLY)
266
if (var.flag & FLAG_PRINT_ONLY) {
267
if (print_msg == NULL)
268
print_msg = entry->creator(pool);
272
/* Detect message. */
273
var.detect_len = var.detect_len + entry->len;
274
pj_get_timestamp(&t1);
275
status = pjsip_find_msg(entry->msg, entry->len, PJ_FALSE, &msg_size);
276
if (status != PJ_SUCCESS) {
277
if (status!=PJSIP_EPARTIALMSG ||
278
entry->expected_status!=STATUS_PARTIAL)
280
app_perror(" error: unable to detect message", status);
284
if (msg_size != entry->len) {
285
PJ_LOG(3,(THIS_FILE, " error: size mismatch"));
288
pj_get_timestamp(&t2);
289
pj_sub_timestamp(&t2, &t1);
290
pj_add_timestamp(&var.detect_time, &t2);
292
if (var.flag & FLAG_DETECT_ONLY)
297
var.parse_len = var.parse_len + entry->len;
298
pj_get_timestamp(&t1);
299
pj_list_init(&err_list);
300
parsed_msg = pjsip_parse_msg(pool, entry->msg, entry->len, &err_list);
301
if (parsed_msg == NULL) {
302
if (entry->expected_status != STATUS_SYNTAX_ERROR) {
304
if (err_list.next != &err_list) {
305
PJ_LOG(3,(THIS_FILE, " Syntax error in line %d col %d",
306
err_list.next->line, err_list.next->col));
311
pj_get_timestamp(&t2);
312
pj_sub_timestamp(&t2, &t1);
313
pj_add_timestamp(&var.parse_time, &t2);
315
if ((var.flag & FLAG_PARSE_ONLY) || entry->creator==NULL)
318
/* Create reference message. */
319
ref_msg = entry->creator(pool);
321
/* Create buffer for comparison. */
322
str1.ptr = (char*)pj_pool_alloc(pool, BUFLEN);
323
str2.ptr = (char*)pj_pool_alloc(pool, BUFLEN);
325
/* Compare message type. */
326
if (parsed_msg->type != ref_msg->type) {
331
/* Compare request or status line. */
332
if (parsed_msg->type == PJSIP_REQUEST_MSG) {
333
pjsip_method *m1 = &parsed_msg->line.req.method;
334
pjsip_method *m2 = &ref_msg->line.req.method;
336
if (pjsip_method_cmp(m1, m2) != 0) {
340
status = pjsip_uri_cmp(PJSIP_URI_IN_REQ_URI,
341
parsed_msg->line.req.uri,
342
ref_msg->line.req.uri);
343
if (status != PJ_SUCCESS) {
344
app_perror(" error: request URI mismatch", status);
349
if (parsed_msg->line.status.code != ref_msg->line.status.code) {
350
PJ_LOG(3,(THIS_FILE, " error: status code mismatch"));
354
if (pj_strcmp(&parsed_msg->line.status.reason,
355
&ref_msg->line.status.reason) != 0)
357
PJ_LOG(3,(THIS_FILE, " error: status text mismatch"));
363
/* Compare headers. */
364
hdr1 = parsed_msg->hdr.next;
365
hdr2 = ref_msg->hdr.next;
367
while (hdr1 != &parsed_msg->hdr && hdr2 != &ref_msg->hdr) {
368
len = pjsip_hdr_print_on(hdr1, str1.ptr, BUFLEN);
373
str1.ptr[len] = '\0';
376
len = pjsip_hdr_print_on(hdr2, str2.ptr, BUFLEN);
381
str2.ptr[len] = '\0';
384
if (pj_strcmp(&str1, &str2) != 0) {
386
PJ_LOG(3,(THIS_FILE, " error: header string mismatch:\n"
389
str1.ptr, str2.ptr));
397
if (hdr1 != &parsed_msg->hdr || hdr2 != &ref_msg->hdr) {
403
if (parsed_msg->body==NULL && ref_msg->body==NULL)
406
/* Compare msg body length. */
407
if (parsed_msg->body->len != ref_msg->body->len) {
412
/* Compare msg body content type. */
413
if (pj_strcmp(&parsed_msg->body->content_type.type,
414
&ref_msg->body->content_type.type) != 0) {
418
if (pj_strcmp(&parsed_msg->body->content_type.subtype,
419
&ref_msg->body->content_type.subtype) != 0) {
424
/* Compare body content. */
425
str1.slen = parsed_msg->body->print_body(parsed_msg->body,
426
msgbuf1, sizeof(msgbuf1));
433
str2.slen = ref_msg->body->print_body(ref_msg->body,
434
msgbuf2, sizeof(msgbuf2));
441
if (pj_strcmp(&str1, &str2) != 0) {
448
var.print_len = var.print_len + entry->len;
449
pj_get_timestamp(&t1);
450
if (var.flag && FLAG_PRINT_ONLY)
452
len = pjsip_msg_print(ref_msg, msgbuf1, PJSIP_MAX_PKT_LEN);
457
pj_get_timestamp(&t2);
458
pj_sub_timestamp(&t2, &t1);
459
pj_add_timestamp(&var.print_time, &t2);
469
static pjsip_msg *create_msg0(pj_pool_t *pool)
473
pjsip_name_addr *name_addr;
475
pjsip_fromto_hdr *fromto;
477
pjsip_clen_hdr *clen;
478
pjsip_cseq_hdr *cseq;
479
pjsip_contact_hdr *contact;
480
pjsip_ctype_hdr *ctype;
481
pjsip_routing_hdr *routing;
483
pjsip_generic_string_hdr *generic;
487
msg = pjsip_msg_create(pool, PJSIP_REQUEST_MSG);
489
/* "INVITE sip:user@foo SIP/2.0\n" */
490
pjsip_method_set(&msg->line.req.method, PJSIP_INVITE_METHOD);
491
url = pjsip_sip_uri_create(pool, 0);
492
msg->line.req.uri = (pjsip_uri*)url;
493
pj_strdup2(pool, &url->user, "user");
494
pj_strdup2(pool, &url->host, "foo");
496
/* "From: Hi I'm Joe <sip:joe.user@bar.otherdomain.com>;tag=123457890123456\r" */
497
fromto = pjsip_from_hdr_create(pool);
498
pjsip_msg_add_hdr(msg, (pjsip_hdr*)fromto);
499
pj_strdup2(pool, &fromto->tag, "123457890123456");
500
name_addr = pjsip_name_addr_create(pool);
501
fromto->uri = (pjsip_uri*)name_addr;
502
pj_strdup2(pool, &name_addr->display, "Hi I'm Joe");
503
url = pjsip_sip_uri_create(pool, 0);
504
name_addr->uri = (pjsip_uri*)url;
505
pj_strdup2(pool, &url->user, "joe.user");
506
pj_strdup2(pool, &url->host, "bar.otherdomain.com");
508
/* "To: Fellow User <sip:user@foo.bar.domain.com>\r\n" */
509
fromto = pjsip_to_hdr_create(pool);
510
pjsip_msg_add_hdr(msg, (pjsip_hdr*)fromto);
511
name_addr = pjsip_name_addr_create(pool);
512
fromto->uri = (pjsip_uri*)name_addr;
513
pj_strdup2(pool, &name_addr->display, "Fellow User");
514
url = pjsip_sip_uri_create(pool, 0);
515
name_addr->uri = (pjsip_uri*)url;
516
pj_strdup2(pool, &url->user, "user");
517
pj_strdup2(pool, &url->host, "foo.bar.domain.com");
519
/* "Call-ID: 12345678901234567890@bar\r\n" */
520
cid = pjsip_cid_hdr_create(pool);
521
pjsip_msg_add_hdr(msg, (pjsip_hdr*)cid);
522
pj_strdup2(pool, &cid->id, "12345678901234567890@bar");
524
/* "Content-Length: 0\r\n" */
525
clen = pjsip_clen_hdr_create(pool);
526
pjsip_msg_add_hdr(msg, (pjsip_hdr*)clen);
529
/* "CSeq: 123456 INVITE\n" */
530
cseq = pjsip_cseq_hdr_create(pool);
531
pjsip_msg_add_hdr(msg, (pjsip_hdr*)cseq);
533
pjsip_method_set(&cseq->method, PJSIP_INVITE_METHOD);
535
/* "Contact: <sip:joe@bar>;q=0.5;expires=3600*/
536
contact = pjsip_contact_hdr_create(pool);
537
pjsip_msg_add_hdr(msg, (pjsip_hdr*)contact);
538
contact->q1000 = 500;
539
contact->expires = 3600;
540
name_addr = pjsip_name_addr_create(pool);
541
contact->uri = (pjsip_uri*)name_addr;
542
url = pjsip_sip_uri_create(pool, 0);
543
name_addr->uri = (pjsip_uri*)url;
544
pj_strdup2(pool, &url->user, "joe");
545
pj_strdup2(pool, &url->host, "bar");
547
/*, sip:user@host;q=0.500\r" */
548
contact = pjsip_contact_hdr_create(pool);
549
pjsip_msg_add_hdr(msg, (pjsip_hdr*)contact);
550
contact->q1000 = 500;
551
name_addr = pjsip_name_addr_create(pool);
552
contact->uri = (pjsip_uri*)name_addr;
553
url = pjsip_sip_uri_create(pool, 0);
554
name_addr->uri = (pjsip_uri*)url;
555
pj_strdup2(pool, &url->user, "user");
556
pj_strdup2(pool, &url->host, "host");
558
/* " ,sip:user2@host2\n" */
559
contact = pjsip_contact_hdr_create(pool);
560
pjsip_msg_add_hdr(msg, (pjsip_hdr*)contact);
561
name_addr = pjsip_name_addr_create(pool);
562
contact->uri = (pjsip_uri*)name_addr;
563
url = pjsip_sip_uri_create(pool, 0);
564
name_addr->uri = (pjsip_uri*)url;
565
pj_strdup2(pool, &url->user, "user2");
566
pj_strdup2(pool, &url->host, "host2");
568
/* "Content-Type: text/html; charset=ISO-8859-4\r" */
569
ctype = pjsip_ctype_hdr_create(pool);
570
pjsip_msg_add_hdr(msg, (pjsip_hdr*)ctype);
571
pj_strdup2(pool, &ctype->media.type, "text");
572
pj_strdup2(pool, &ctype->media.subtype, "html");
573
prm = PJ_POOL_ALLOC_T(pool, pjsip_param);
574
prm->name = pj_str("charset");
575
prm->value = pj_str("ISO-8859-4");
576
pj_list_push_back(&ctype->media.param, prm);
578
/* "Route: <sip:bigbox3.site3.atlanta.com;lr>,\r\n" */
579
routing = pjsip_route_hdr_create(pool);
580
pjsip_msg_add_hdr(msg, (pjsip_hdr*)routing);
581
url = pjsip_sip_uri_create(pool, 0);
582
routing->name_addr.uri = (pjsip_uri*)url;
583
pj_strdup2(pool, &url->host, "bigbox3.site3.atlanta.com");
586
/* " <sip:server10.biloxi.com;lr>\r" */
587
routing = pjsip_route_hdr_create(pool);
588
pjsip_msg_add_hdr(msg, (pjsip_hdr*)routing);
589
url = pjsip_sip_uri_create(pool, 0);
590
routing->name_addr.uri = (pjsip_uri*)url;
591
pj_strdup2(pool, &url->host, "server10.biloxi.com");
594
/* "Record-Route: <sip:server10.biloxi.com>,\r\n" */
595
routing = pjsip_rr_hdr_create(pool);
596
pjsip_msg_add_hdr(msg, (pjsip_hdr*)routing);
597
url = pjsip_sip_uri_create(pool, 0);
598
routing->name_addr.uri = (pjsip_uri*)url;
599
pj_strdup2(pool, &url->host, "server10.biloxi.com");
602
/* " <sip:bigbox3.site3.atlanta.com;lr>\n" */
603
routing = pjsip_rr_hdr_create(pool);
604
pjsip_msg_add_hdr(msg, (pjsip_hdr*)routing);
605
url = pjsip_sip_uri_create(pool, 0);
606
routing->name_addr.uri = (pjsip_uri*)url;
607
pj_strdup2(pool, &url->host, "bigbox3.site3.atlanta.com");
610
/* "Via: SIP/2.0/SCTP bigbox3.site3.atlanta.com;branch=z9hG4bK77ef4c230\n" */
611
via = pjsip_via_hdr_create(pool);
612
pjsip_msg_add_hdr(msg, (pjsip_hdr*)via);
613
pj_strdup2(pool, &via->transport, "SCTP");
614
pj_strdup2(pool, &via->sent_by.host, "bigbox3.site3.atlanta.com");
615
pj_strdup2(pool, &via->branch_param, "z9hG4bK77ef4c230");
617
/* "Via: SIP/2.0/UDP pc33.atlanta.com;branch=z9hG4bKnashds8\n"
618
" ;received=192.0.2.1\r\n" */
619
via = pjsip_via_hdr_create(pool);
620
pjsip_msg_add_hdr(msg, (pjsip_hdr*)via);
621
pj_strdup2(pool, &via->transport, "UDP");
622
pj_strdup2(pool, &via->sent_by.host, "pc33.atlanta.com");
623
pj_strdup2(pool, &via->branch_param, "z9hG4bKnashds8");
624
pj_strdup2(pool, &via->recvd_param, "192.0.2.1");
627
/* "Via: SIP/2.0/UDP 10.2.1.1, */
628
via = pjsip_via_hdr_create(pool);
629
pjsip_msg_add_hdr(msg, (pjsip_hdr*)via);
630
pj_strdup2(pool, &via->transport, "UDP");
631
pj_strdup2(pool, &via->sent_by.host, "10.2.1.1");
634
/*SIP/2.0/TCP 192.168.1.1\n" */
635
via = pjsip_via_hdr_create(pool);
636
pjsip_msg_add_hdr(msg, (pjsip_hdr*)via);
637
pj_strdup2(pool, &via->transport, "TCP");
638
pj_strdup2(pool, &via->sent_by.host, "192.168.1.1");
640
/* "Organization: \r" */
641
str.ptr = "Organization";
643
generic = pjsip_generic_string_hdr_create(pool, &str, NULL);
644
pjsip_msg_add_hdr(msg, (pjsip_hdr*)generic);
645
generic->hvalue.ptr = NULL;
646
generic->hvalue.slen = 0;
648
/* "Max-Forwards: 70\n" */
649
str.ptr = "Max-Forwards";
651
generic = pjsip_generic_string_hdr_create(pool, &str, NULL);
652
pjsip_msg_add_hdr(msg, (pjsip_hdr*)generic);
655
generic->hvalue = str;
657
/* "X-Header: \r\n" */
658
str.ptr = "X-Header";
660
generic = pjsip_generic_string_hdr_create(pool, &str, NULL);
661
pjsip_msg_add_hdr(msg, (pjsip_hdr*)generic);
664
generic->hvalue = str;
666
/* P-Associated-URI:\r\n */
667
str.ptr = "P-Associated-URI";
669
generic = pjsip_generic_string_hdr_create(pool, &str, NULL);
670
pjsip_msg_add_hdr(msg, (pjsip_hdr*)generic);
673
generic->hvalue = str;
678
static pjsip_msg *create_msg1(pj_pool_t *pool)
681
pjsip_route_hdr *route;
682
pjsip_name_addr *name_addr;
684
pjsip_max_fwd_hdr *max_fwd;
686
pjsip_from_hdr *from;
687
pjsip_contact_hdr *contact;
688
pjsip_ctype_hdr *ctype;
690
pjsip_clen_hdr *clen;
691
pjsip_cseq_hdr *cseq;
692
pjsip_msg *msg = pjsip_msg_create(pool, PJSIP_RESPONSE_MSG);
693
pjsip_msg_body *body;
695
//"SIP/2.0 200 OK\r\n"
696
msg->line.status.code = 200;
697
msg->line.status.reason = pj_str("OK");
699
//"Via: SIP/2.0/SCTP server10.biloxi.com;branch=z9hG4bKnashds8;rport;received=192.0.2.1\r\n"
700
via = pjsip_via_hdr_create(pool);
701
pjsip_msg_add_hdr(msg, (pjsip_hdr*)via);
702
via->transport = pj_str("SCTP");
703
via->sent_by.host = pj_str("server10.biloxi.com");
704
via->branch_param = pj_str("z9hG4bKnashds8");
705
via->rport_param = 0;
706
via->recvd_param = pj_str("192.0.2.1");
708
//"Via: SIP/2.0/UDP bigbox3.site3.atlanta.com;branch=z9hG4bK77ef4c2312983.1;received=192.0.2.2\r\n"
709
via = pjsip_via_hdr_create(pool);
710
pjsip_msg_add_hdr(msg, (pjsip_hdr*)via);
711
via->transport = pj_str("UDP");
712
via->sent_by.host = pj_str("bigbox3.site3.atlanta.com");
713
via->branch_param = pj_str("z9hG4bK77ef4c2312983.1");
714
via->recvd_param = pj_str("192.0.2.2");
716
//"Via: SIP/2.0/UDP pc33.atlanta.com;branch=z9hG4bK776asdhds ;received=192.0.2.3\r\n"
717
via = pjsip_via_hdr_create(pool);
718
pjsip_msg_add_hdr(msg, (pjsip_hdr*)via);
719
via->transport = pj_str("UDP");
720
via->sent_by.host = pj_str("pc33.atlanta.com");
721
via->branch_param = pj_str("z9hG4bK776asdhds");
722
via->recvd_param = pj_str("192.0.2.3");
724
//"Route: <sip:proxy.sipprovider.com>\r\n"
725
route = pjsip_route_hdr_create(pool);
726
pjsip_msg_add_hdr(msg, (pjsip_hdr*)route);
727
url = pjsip_sip_uri_create(pool, PJ_FALSE);
728
route->name_addr.uri = (pjsip_uri*)url;
729
url->host = pj_str("proxy.sipprovider.com");
731
//"Route: <sip:proxy.supersip.com:5060>\r\n"
732
route = pjsip_route_hdr_create(pool);
733
pjsip_msg_add_hdr(msg, (pjsip_hdr*)route);
734
url = pjsip_sip_uri_create(pool, PJ_FALSE);
735
route->name_addr.uri = (pjsip_uri*)url;
736
url->host = pj_str("proxy.supersip.com");
739
//"Max-Forwards: 70\r\n"
740
max_fwd = pjsip_max_fwd_hdr_create(pool, 70);
741
pjsip_msg_add_hdr(msg, (pjsip_hdr*)max_fwd);
743
//"To: Bob <sip:bob@biloxi.com>;tag=a6c85cf\r\n"
744
to = pjsip_to_hdr_create(pool);
745
pjsip_msg_add_hdr(msg, (pjsip_hdr*)to);
746
name_addr = pjsip_name_addr_create(pool);
747
name_addr->display = pj_str("Bob");
748
to->uri = (pjsip_uri*)name_addr;
749
url = pjsip_sip_uri_create(pool, PJ_FALSE);
750
name_addr->uri = (pjsip_uri*)url;
751
url->user = pj_str("bob");
752
url->host = pj_str("biloxi.com");
753
to->tag = pj_str("a6c85cf");
755
//"From: Alice <sip:alice@atlanta.com>;tag=1928301774\r\n"
756
from = pjsip_from_hdr_create(pool);
757
pjsip_msg_add_hdr(msg, (pjsip_hdr*)from);
758
name_addr = pjsip_name_addr_create(pool);
759
name_addr->display = pj_str("Alice");
760
from->uri = (pjsip_uri*)name_addr;
761
url = pjsip_sip_uri_create(pool, PJ_FALSE);
762
name_addr->uri = (pjsip_uri*)url;
763
url->user = pj_str("alice");
764
url->host = pj_str("atlanta.com");
765
from->tag = pj_str("1928301774");
767
//"Call-ID: a84b4c76e66710@pc33.atlanta.com\r\n"
768
cid = pjsip_cid_hdr_create(pool);
769
pjsip_msg_add_hdr(msg, (pjsip_hdr*)cid);
770
cid->id = pj_str("a84b4c76e66710@pc33.atlanta.com");
772
//"CSeq: 314159 INVITE\r\n"
773
cseq = pjsip_cseq_hdr_create(pool);
774
pjsip_msg_add_hdr(msg, (pjsip_hdr*)cseq);
776
pjsip_method_set(&cseq->method, PJSIP_INVITE_METHOD);
778
//"Contact: <sips:bob@192.0.2.4>\r\n"
779
contact = pjsip_contact_hdr_create(pool);
780
pjsip_msg_add_hdr(msg, (pjsip_hdr*)contact);
781
name_addr = pjsip_name_addr_create(pool);
782
contact->uri = (pjsip_uri*)name_addr;
783
url = pjsip_sip_uri_create(pool, PJ_TRUE);
784
name_addr->uri = (pjsip_uri*)url;
785
url->user = pj_str("bob");
786
url->host = pj_str("192.0.2.4");
788
//"Content-Type: application/sdp\r\n"
789
ctype = pjsip_ctype_hdr_create(pool);
790
pjsip_msg_add_hdr(msg, (pjsip_hdr*)ctype);
791
ctype->media.type = pj_str("application");
792
ctype->media.subtype = pj_str("sdp");
794
//"Content-Length: 150\r\n"
795
clen = pjsip_clen_hdr_create(pool);
796
pjsip_msg_add_hdr(msg, (pjsip_hdr*)clen);
800
body = PJ_POOL_ZALLOC_T(pool, pjsip_msg_body);
802
body->content_type.type = pj_str("application");
803
body->content_type.subtype = pj_str("sdp");
806
"o=alice 53655765 2353687637 IN IP4 pc33.atlanta.com\r\n"
809
"c=IN IP4 pc33.atlanta.com\r\n"
810
"m=audio 3456 RTP/AVP 0 1 3 99\r\n"
811
"a=rtpmap:0 PCMU/8000\r\n";
812
body->len = pj_ansi_strlen((const char*) body->data);
813
body->print_body = &pjsip_print_text_body;
818
/*****************************************************************************/
820
static pj_status_t simple_test(void)
822
char stbuf[] = "SIP/2.0 180 Ringing like it never rings before";
824
pjsip_status_line st_line;
827
PJ_LOG(3,(THIS_FILE, " simple test.."));
829
status = pjsip_parse_status_line(stbuf, pj_ansi_strlen(stbuf), &st_line);
830
if (status != PJ_SUCCESS)
833
for (i=0; i<PJ_ARRAY_SIZE(test_array); ++i) {
835
pool = pjsip_endpt_create_pool(endpt, NULL, POOL_SIZE, POOL_SIZE);
836
status = test_entry( pool, &test_array[i] );
837
pjsip_endpt_release_pool(endpt, pool);
839
if (status != PJ_SUCCESS)
847
#if INCLUDE_BENCHMARKS
848
static int msg_benchmark(unsigned *p_detect, unsigned *p_parse,
855
pj_highprec_t avg_detect, avg_parse, avg_print, kbytes;
856
pj_status_t status = PJ_SUCCESS;
858
pj_bzero(&var, sizeof(var));
861
for (loop=0; loop<LOOP; ++loop) {
862
for (i=0; i<(int)PJ_ARRAY_SIZE(test_array); ++i) {
863
pool = pjsip_endpt_create_pool(endpt, NULL, POOL_SIZE, POOL_SIZE);
864
status = test_entry( pool, &test_array[i] );
865
pjsip_endpt_release_pool(endpt, pool);
867
if (status != PJ_SUCCESS)
872
kbytes = var.detect_len;
873
pj_highprec_mod(kbytes, 1000000);
874
pj_highprec_div(kbytes, 100000);
875
elapsed = pj_elapsed_time(&zero, &var.detect_time);
876
avg_detect = pj_elapsed_usec(&zero, &var.detect_time);
877
pj_highprec_mul(avg_detect, AVERAGE_MSG_LEN);
878
pj_highprec_div(avg_detect, var.detect_len);
879
avg_detect = 1000000 / avg_detect;
882
" %u.%u MB detected in %d.%03ds (avg=%d msg detection/sec)",
883
(unsigned)(var.detect_len/1000000), (unsigned)kbytes,
884
elapsed.sec, elapsed.msec,
885
(unsigned)avg_detect));
886
*p_detect = (unsigned)avg_detect;
888
kbytes = var.parse_len;
889
pj_highprec_mod(kbytes, 1000000);
890
pj_highprec_div(kbytes, 100000);
891
elapsed = pj_elapsed_time(&zero, &var.parse_time);
892
avg_parse = pj_elapsed_usec(&zero, &var.parse_time);
893
pj_highprec_mul(avg_parse, AVERAGE_MSG_LEN);
894
pj_highprec_div(avg_parse, var.parse_len);
895
avg_parse = 1000000 / avg_parse;
898
" %u.%u MB parsed in %d.%03ds (avg=%d msg parsing/sec)",
899
(unsigned)(var.parse_len/1000000), (unsigned)kbytes,
900
elapsed.sec, elapsed.msec,
901
(unsigned)avg_parse));
902
*p_parse = (unsigned)avg_parse;
904
kbytes = var.print_len;
905
pj_highprec_mod(kbytes, 1000000);
906
pj_highprec_div(kbytes, 100000);
907
elapsed = pj_elapsed_time(&zero, &var.print_time);
908
avg_print = pj_elapsed_usec(&zero, &var.print_time);
909
pj_highprec_mul(avg_print, AVERAGE_MSG_LEN);
910
pj_highprec_div(avg_print, var.print_len);
911
avg_print = 1000000 / avg_print;
914
" %u.%u MB printed in %d.%03ds (avg=%d msg print/sec)",
915
(unsigned)(var.print_len/1000000), (unsigned)kbytes,
916
elapsed.sec, elapsed.msec,
917
(unsigned)avg_print));
919
*p_print = (unsigned)avg_print;
922
#endif /* INCLUDE_BENCHMARKS */
924
/*****************************************************************************/
925
/* Test various header parsing and production */
926
static int hdr_test_success(pjsip_hdr *h);
927
static int hdr_test_accept0(pjsip_hdr *h);
928
static int hdr_test_accept1(pjsip_hdr *h);
929
static int hdr_test_accept2(pjsip_hdr *h);
930
static int hdr_test_allow0(pjsip_hdr *h);
931
static int hdr_test_authorization(pjsip_hdr *h);
932
static int hdr_test_cid(pjsip_hdr *h);
933
static int hdr_test_contact0(pjsip_hdr *h);
934
static int hdr_test_contact1(pjsip_hdr *h);
935
static int hdr_test_contact_q0(pjsip_hdr *h);
936
static int hdr_test_contact_q1(pjsip_hdr *h);
937
static int hdr_test_contact_q2(pjsip_hdr *h);
938
static int hdr_test_contact_q3(pjsip_hdr *h);
939
static int hdr_test_contact_q4(pjsip_hdr *h);
940
static int hdr_test_content_length(pjsip_hdr *h);
941
static int hdr_test_content_type(pjsip_hdr *h);
942
static int hdr_test_from(pjsip_hdr *h);
943
static int hdr_test_proxy_authenticate(pjsip_hdr *h);
944
static int hdr_test_record_route(pjsip_hdr *h);
945
static int hdr_test_supported(pjsip_hdr *h);
946
static int hdr_test_to(pjsip_hdr *h);
947
static int hdr_test_via(pjsip_hdr *h);
948
static int hdr_test_via_ipv6_1(pjsip_hdr *h);
949
static int hdr_test_via_ipv6_2(pjsip_hdr *h);
950
static int hdr_test_via_ipv6_3(pjsip_hdr *h);
951
static int hdr_test_retry_after1(pjsip_hdr *h);
952
static int hdr_test_subject_utf(pjsip_hdr *h);
955
#define GENERIC_PARAM "p0=a;p1=\"ab:;cd\";p2=ab%3acd;p3"
956
#define GENERIC_PARAM_PARSED "p0=a;p1=\"ab:;cd\";p2=ab:cd;p3"
957
#define PARAM_CHAR "][/:&+$"
958
#define SIMPLE_ADDR_SPEC "sip:host"
959
#define ADDR_SPEC SIMPLE_ADDR_SPEC ";"PARAM_CHAR"="PARAM_CHAR ";p1=\";\""
960
#define NAME_ADDR "<" ADDR_SPEC ">"
962
#define HDR_FLAG_PARSE_FAIL 1
963
#define HDR_FLAG_DONT_PRINT 2
970
int (*test)(pjsip_hdr*);
982
/* Overflowing generic string header */
984
"a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, " \
985
"a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, " \
986
"a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, " \
987
"a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, " \
988
"a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, " \
989
"a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, " \
990
"a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, " \
991
"a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a, a",
999
"application/*, text/plain",
1004
/* Accept with params */
1006
"application/*;p1=v1, text/plain",
1018
/* Authorization, testing which params should be quoted */
1019
"Authorization", NULL,
1020
"Digest username=\"username\", realm=\"realm\", nonce=\"nonce\", " \
1021
"uri=\"sip:domain\", response=\"RESPONSE\", algorithm=MD5, " \
1022
"cnonce=\"CNONCE\", opaque=\"OPAQUE\", qop=auth, nc=00000001",
1023
&hdr_test_authorization
1029
"-.!%*_+`'~()<>:\\\"/[]?{}",
1034
/* Parameter belong to hparam */
1036
SIMPLE_ADDR_SPEC ";p1=v1",
1042
/* generic-param in Contact header */
1044
NAME_ADDR ";" GENERIC_PARAM,
1049
/* q=0 parameter in Contact header */
1052
&hdr_test_contact_q0,
1057
/* q=0.5 parameter in Contact header */
1060
&hdr_test_contact_q1
1064
/* q=1 parameter in Contact header */
1067
&hdr_test_contact_q2
1071
/* q=1.0 parameter in Contact header */
1074
&hdr_test_contact_q3,
1079
/* q=1.1 parameter in Contact header */
1081
NAME_ADDR ";q=1.15",
1082
&hdr_test_contact_q4
1086
/* Content-Length */
1087
"Content-Length", "l",
1089
&hdr_test_content_length
1093
/* Content-Type, with generic-param */
1094
"Content-Type", "c",
1095
"application/sdp" ";" GENERIC_PARAM,
1096
&hdr_test_content_type,
1101
/* From, testing parameters and generic-param */
1103
NAME_ADDR ";" GENERIC_PARAM,
1108
/* Proxy-Authenticate, testing which params should be quoted */
1109
"Proxy-Authenticate", NULL,
1110
"Digest realm=\"realm\",domain=\"sip:domain\",nonce=\"nonce\"," \
1111
"opaque=\"opaque\",stale=true,algorithm=MD5,qop=\"auth\"",
1112
&hdr_test_proxy_authenticate
1116
/* Record-Route, param belong to header */
1117
"Record-Route", NULL,
1118
NAME_ADDR ";" GENERIC_PARAM,
1119
&hdr_test_record_route
1123
/* Empty Supported */
1126
&hdr_test_supported,
1132
NAME_ADDR ";" GENERIC_PARAM,
1139
"SIP/2.0/XYZ host" ";" GENERIC_PARAM,
1146
"SIP/2.0/UDP [::1]",
1147
&hdr_test_via_ipv6_1
1153
"SIP/2.0/UDP [::1]:5061",
1154
&hdr_test_via_ipv6_2
1160
"SIP/2.0/UDP [::1];rport=5061;received=::2",
1161
&hdr_test_via_ipv6_3
1165
/* Retry-After header with comment */
1166
"Retry-After", NULL,
1167
"10(Already Pending Register)",
1168
&hdr_test_retry_after1
1172
/* Non-ASCII UTF-8 characters in Subject */
1175
&hdr_test_subject_utf
1179
static int hdr_test_success(pjsip_hdr *h)
1186
static int hdr_test_accept0(pjsip_hdr *h)
1188
pjsip_accept_hdr *hdr = (pjsip_accept_hdr*)h;
1190
if (h->type != PJSIP_H_ACCEPT)
1193
if (hdr->count != 0)
1199
/* "application/ *, text/plain\r\n" */
1200
static int hdr_test_accept1(pjsip_hdr *h)
1202
pjsip_accept_hdr *hdr = (pjsip_accept_hdr*)h;
1204
if (h->type != PJSIP_H_ACCEPT)
1207
if (hdr->count != 2)
1210
if (pj_strcmp2(&hdr->values[0], "application/*"))
1213
if (pj_strcmp2(&hdr->values[1], "text/plain"))
1219
/* "application/ *;p1=v1, text/plain\r\n" */
1220
static int hdr_test_accept2(pjsip_hdr *h)
1222
pjsip_accept_hdr *hdr = (pjsip_accept_hdr*)h;
1224
if (h->type != PJSIP_H_ACCEPT)
1227
if (hdr->count != 2)
1230
if (pj_strcmp2(&hdr->values[0], "application/*;p1=v1"))
1233
if (pj_strcmp2(&hdr->values[1], "text/plain"))
1240
static int hdr_test_allow0(pjsip_hdr *h)
1242
pjsip_allow_hdr *hdr = (pjsip_allow_hdr*)h;
1244
if (h->type != PJSIP_H_ALLOW)
1247
if (hdr->count != 0)
1256
"Digest username=\"username\", realm=\"realm\", nonce=\"nonce\", " \
1257
"uri=\"sip:domain\", response=\"RESPONSE\", algorithm=MD5, " \
1258
"cnonce=\"CNONCE\", opaque=\"OPAQUE\", qop=auth, nc=00000001",
1260
static int hdr_test_authorization(pjsip_hdr *h)
1262
pjsip_authorization_hdr *hdr = (pjsip_authorization_hdr*)h;
1264
if (h->type != PJSIP_H_AUTHORIZATION)
1267
if (pj_strcmp2(&hdr->scheme, "Digest"))
1270
if (pj_strcmp2(&hdr->credential.digest.username, "username"))
1273
if (pj_strcmp2(&hdr->credential.digest.realm, "realm"))
1276
if (pj_strcmp2(&hdr->credential.digest.nonce, "nonce"))
1279
if (pj_strcmp2(&hdr->credential.digest.uri, "sip:domain"))
1282
if (pj_strcmp2(&hdr->credential.digest.response, "RESPONSE"))
1285
if (pj_strcmp2(&hdr->credential.digest.algorithm, "MD5"))
1288
if (pj_strcmp2(&hdr->credential.digest.cnonce, "CNONCE"))
1291
if (pj_strcmp2(&hdr->credential.digest.opaque, "OPAQUE"))
1294
if (pj_strcmp2(&hdr->credential.digest.qop, "auth"))
1297
if (pj_strcmp2(&hdr->credential.digest.nc, "00000001"))
1305
"-.!%*_+`'~()<>:\\\"/[]?{}\r\n"
1307
static int hdr_test_cid(pjsip_hdr *h)
1309
pjsip_cid_hdr *hdr = (pjsip_cid_hdr*)h;
1311
if (h->type != PJSIP_H_CALL_ID)
1314
if (pj_strcmp2(&hdr->id, "-.!%*_+`'~()<>:\\\"/[]?{}"))
1321
#define SIMPLE_ADDR_SPEC "sip:host"
1323
static int test_simple_addr_spec(pjsip_uri *uri)
1325
pjsip_sip_uri *sip_uri = (pjsip_sip_uri *)pjsip_uri_get_uri(uri);
1327
if (!PJSIP_URI_SCHEME_IS_SIP(uri))
1330
if (pj_strcmp2(&sip_uri->host, "host"))
1333
if (sip_uri->port != 0)
1340
#define PARAM_CHAR "][/:&+$"
1341
#define SIMPLE_ADDR_SPEC "sip:host"
1342
#define ADDR_SPEC SIMPLE_ADDR_SPEC ";"PARAM_CHAR"="PARAM_CHAR ";p1=\";\""
1343
#define NAME_ADDR "<" ADDR_SPEC ">"
1345
static int nameaddr_test(void *uri)
1347
pjsip_sip_uri *sip_uri=(pjsip_sip_uri *)pjsip_uri_get_uri((pjsip_uri*)uri);
1351
if (!PJSIP_URI_SCHEME_IS_SIP(uri))
1354
rc = test_simple_addr_spec((pjsip_uri*)sip_uri);
1358
if (pj_list_size(&sip_uri->other_param) != 2)
1361
param = sip_uri->other_param.next;
1363
if (pj_strcmp2(¶m->name, PARAM_CHAR))
1366
if (pj_strcmp2(¶m->value, PARAM_CHAR))
1369
param = param->next;
1370
if (pj_strcmp2(¶m->name, "p1"))
1372
if (pj_strcmp2(¶m->value, "\";\""))
1379
#define GENERIC_PARAM "p0=a;p1=\"ab:;cd\";p2=ab%3acd;p3"
1381
static int generic_param_test(pjsip_param *param_head)
1385
if (pj_list_size(param_head) != 4)
1388
param = param_head->next;
1390
if (pj_strcmp2(¶m->name, "p0"))
1392
if (pj_strcmp2(¶m->value, "a"))
1395
param = param->next;
1396
if (pj_strcmp2(¶m->name, "p1"))
1398
if (pj_strcmp2(¶m->value, "\"ab:;cd\""))
1401
param = param->next;
1402
if (pj_strcmp2(¶m->name, "p2"))
1404
if (pj_strcmp2(¶m->value, "ab:cd"))
1407
param = param->next;
1408
if (pj_strcmp2(¶m->name, "p3"))
1410
if (pj_strcmp2(¶m->value, ""))
1419
SIMPLE_ADDR_SPEC ";p1=v1\r\n"
1421
static int hdr_test_contact0(pjsip_hdr *h)
1423
pjsip_contact_hdr *hdr = (pjsip_contact_hdr*)h;
1427
if (h->type != PJSIP_H_CONTACT)
1430
rc = test_simple_addr_spec(hdr->uri);
1434
if (pj_list_size(&hdr->other_param) != 1)
1437
param = hdr->other_param.next;
1439
if (pj_strcmp2(¶m->name, "p1"))
1442
if (pj_strcmp2(¶m->value, "v1"))
1449
NAME_ADDR GENERIC_PARAM "\r\n",
1451
static int hdr_test_contact1(pjsip_hdr *h)
1453
pjsip_contact_hdr *hdr = (pjsip_contact_hdr*)h;
1456
if (h->type != PJSIP_H_CONTACT)
1459
rc = nameaddr_test(hdr->uri);
1463
rc = generic_param_test(&hdr->other_param);
1473
static int hdr_test_contact_q0(pjsip_hdr *h)
1475
pjsip_contact_hdr *hdr = (pjsip_contact_hdr*)h;
1478
if (h->type != PJSIP_H_CONTACT)
1481
rc = nameaddr_test(hdr->uri);
1485
if (hdr->q1000 != 0)
1494
static int hdr_test_contact_q1(pjsip_hdr *h)
1496
pjsip_contact_hdr *hdr = (pjsip_contact_hdr*)h;
1499
if (h->type != PJSIP_H_CONTACT)
1502
rc = nameaddr_test(hdr->uri);
1506
if (hdr->q1000 != 500)
1515
static int hdr_test_contact_q2(pjsip_hdr *h)
1517
pjsip_contact_hdr *hdr = (pjsip_contact_hdr*)h;
1520
if (h->type != PJSIP_H_CONTACT)
1523
rc = nameaddr_test(hdr->uri);
1527
if (hdr->q1000 != 1000)
1536
static int hdr_test_contact_q3(pjsip_hdr *h)
1538
pjsip_contact_hdr *hdr = (pjsip_contact_hdr*)h;
1541
if (h->type != PJSIP_H_CONTACT)
1544
rc = nameaddr_test(hdr->uri);
1548
if (hdr->q1000 != 1000)
1557
static int hdr_test_contact_q4(pjsip_hdr *h)
1559
pjsip_contact_hdr *hdr = (pjsip_contact_hdr*)h;
1562
if (h->type != PJSIP_H_CONTACT)
1565
rc = nameaddr_test(hdr->uri);
1569
if (hdr->q1000 != 1150)
1578
static int hdr_test_content_length(pjsip_hdr *h)
1580
pjsip_clen_hdr *hdr = (pjsip_clen_hdr*)h;
1582
if (h->type != PJSIP_H_CONTENT_LENGTH)
1592
"application/sdp" GENERIC_PARAM,
1594
static int hdr_test_content_type(pjsip_hdr *h)
1596
pjsip_ctype_hdr *hdr = (pjsip_ctype_hdr*)h;
1597
const pjsip_param *prm;
1599
if (h->type != PJSIP_H_CONTENT_TYPE)
1602
if (pj_strcmp2(&hdr->media.type, "application"))
1605
if (pj_strcmp2(&hdr->media.subtype, "sdp"))
1608
/* Currently, if the media parameter contains escaped characters,
1609
* pjsip will print the parameter unescaped.
1611
prm = hdr->media.param.next;
1612
if (prm == &hdr->media.param) return -1940;
1613
if (pj_strcmp2(&prm->name, "p0")) return -1941;
1614
if (pj_strcmp2(&prm->value, "a")) return -1942;
1617
if (prm == &hdr->media.param) return -1950;
1618
if (pj_strcmp2(&prm->name, "p1")) { PJ_LOG(3,("", "%.*s", (int)prm->name.slen, prm->name.ptr)); return -1951; }
1619
if (pj_strcmp2(&prm->value, "\"ab:;cd\"")) { PJ_LOG(3,("", "%.*s", (int)prm->value.slen, prm->value.ptr)); return -1952; }
1622
if (prm == &hdr->media.param) return -1960;
1623
if (pj_strcmp2(&prm->name, "p2")) return -1961;
1624
if (pj_strcmp2(&prm->value, "ab:cd")) return -1962;
1627
if (prm == &hdr->media.param) return -1970;
1628
if (pj_strcmp2(&prm->name, "p3")) return -1971;
1629
if (pj_strcmp2(&prm->value, "")) return -1972;
1635
NAME_ADDR GENERIC_PARAM,
1637
static int hdr_test_from(pjsip_hdr *h)
1639
pjsip_from_hdr *hdr = (pjsip_from_hdr*)h;
1642
if (h->type != PJSIP_H_FROM)
1645
rc = nameaddr_test(hdr->uri);
1649
rc = generic_param_test(&hdr->other_param);
1657
"Digest realm=\"realm\", domain=\"sip:domain\", nonce=\"nonce\", " \
1658
"opaque=\"opaque\", stale=true, algorithm=MD5, qop=\"auth\"",
1660
static int hdr_test_proxy_authenticate(pjsip_hdr *h)
1662
pjsip_proxy_authenticate_hdr *hdr = (pjsip_proxy_authenticate_hdr*)h;
1664
if (h->type != PJSIP_H_PROXY_AUTHENTICATE)
1667
if (pj_strcmp2(&hdr->scheme, "Digest"))
1670
if (pj_strcmp2(&hdr->challenge.digest.realm, "realm"))
1673
if (pj_strcmp2(&hdr->challenge.digest.domain, "sip:domain"))
1676
if (pj_strcmp2(&hdr->challenge.digest.nonce, "nonce"))
1679
if (pj_strcmp2(&hdr->challenge.digest.opaque, "opaque"))
1682
if (hdr->challenge.digest.stale != 1)
1685
if (pj_strcmp2(&hdr->challenge.digest.algorithm, "MD5"))
1688
if (pj_strcmp2(&hdr->challenge.digest.qop, "auth"))
1695
NAME_ADDR GENERIC_PARAM,
1697
static int hdr_test_record_route(pjsip_hdr *h)
1699
pjsip_rr_hdr *hdr = (pjsip_rr_hdr*)h;
1702
if (h->type != PJSIP_H_RECORD_ROUTE)
1705
rc = nameaddr_test(&hdr->name_addr);
1709
rc = generic_param_test(&hdr->other_param);
1720
static int hdr_test_supported(pjsip_hdr *h)
1722
pjsip_supported_hdr *hdr = (pjsip_supported_hdr*)h;
1724
if (h->type != PJSIP_H_SUPPORTED)
1727
if (hdr->count != 0)
1734
NAME_ADDR GENERIC_PARAM,
1736
static int hdr_test_to(pjsip_hdr *h)
1738
pjsip_to_hdr *hdr = (pjsip_to_hdr*)h;
1741
if (h->type != PJSIP_H_TO)
1744
rc = nameaddr_test(hdr->uri);
1748
rc = generic_param_test(&hdr->other_param);
1756
"SIP/2.0 host" GENERIC_PARAM
1758
static int hdr_test_via(pjsip_hdr *h)
1760
pjsip_via_hdr *hdr = (pjsip_via_hdr*)h;
1763
if (h->type != PJSIP_H_VIA)
1766
if (pj_strcmp2(&hdr->transport, "XYZ"))
1769
if (pj_strcmp2(&hdr->sent_by.host, "host"))
1772
if (hdr->sent_by.port != 0)
1775
rc = generic_param_test(&hdr->other_param);
1786
static int hdr_test_via_ipv6_1(pjsip_hdr *h)
1788
pjsip_via_hdr *hdr = (pjsip_via_hdr*)h;
1790
if (h->type != PJSIP_H_VIA)
1793
if (pj_strcmp2(&hdr->transport, "UDP"))
1796
if (pj_strcmp2(&hdr->sent_by.host, "::1"))
1799
if (hdr->sent_by.port != 0)
1805
/* "SIP/2.0/UDP [::1]:5061" */
1806
static int hdr_test_via_ipv6_2(pjsip_hdr *h)
1808
pjsip_via_hdr *hdr = (pjsip_via_hdr*)h;
1810
if (h->type != PJSIP_H_VIA)
1813
if (pj_strcmp2(&hdr->transport, "UDP"))
1816
if (pj_strcmp2(&hdr->sent_by.host, "::1"))
1819
if (hdr->sent_by.port != 5061)
1825
/* "SIP/2.0/UDP [::1];rport=5061;received=::2" */
1826
static int hdr_test_via_ipv6_3(pjsip_hdr *h)
1828
pjsip_via_hdr *hdr = (pjsip_via_hdr*)h;
1830
if (h->type != PJSIP_H_VIA)
1833
if (pj_strcmp2(&hdr->transport, "UDP"))
1836
if (pj_strcmp2(&hdr->sent_by.host, "::1"))
1839
if (hdr->sent_by.port != 0)
1842
if (pj_strcmp2(&hdr->recvd_param, "::2"))
1845
if (hdr->rport_param != 5061)
1851
/* "10(Already Pending Register)" */
1852
static int hdr_test_retry_after1(pjsip_hdr *h)
1854
pjsip_retry_after_hdr *hdr = (pjsip_retry_after_hdr*)h;
1856
if (h->type != PJSIP_H_RETRY_AFTER)
1859
if (hdr->ivalue != 10)
1862
if (pj_strcmp2(&hdr->comment, "Already Pending Register"))
1868
/* Subject: \xC0\x81 */
1869
static int hdr_test_subject_utf(pjsip_hdr *h)
1871
pjsip_subject_hdr *hdr = (pjsip_subject_hdr*)h;
1873
if (pj_strcmp2(&h->name, "Subject"))
1876
if (pj_strcmp2(&hdr->hvalue, "\xC0\x81"))
1882
static int hdr_test(void)
1886
PJ_LOG(3,(THIS_FILE, " testing header parsing.."));
1888
for (i=0; i<PJ_ARRAY_SIZE(hdr_test_data); ++i) {
1889
struct hdr_test_t *test = &hdr_test_data[i];
1891
int len, parsed_len;
1893
pjsip_hdr *parsed_hdr1=NULL, *parsed_hdr2=NULL;
1894
char *input, *output;
1895
#if defined(PJSIP_UNESCAPE_IN_PLACE) && PJSIP_UNESCAPE_IN_PLACE!=0
1896
static char hcontent[1024];
1902
pool = pjsip_endpt_create_pool(endpt, NULL, POOL_SIZE, POOL_SIZE);
1904
/* Parse the header */
1905
hname = pj_str(test->hname);
1906
len = strlen(test->hcontent);
1907
#if defined(PJSIP_UNESCAPE_IN_PLACE) && PJSIP_UNESCAPE_IN_PLACE!=0
1908
PJ_ASSERT_RETURN(len < sizeof(hcontent), PJSIP_EMSGTOOLONG);
1909
strcpy(hcontent, test->hcontent);
1911
hcontent = test->hcontent;
1914
parsed_hdr1 = (pjsip_hdr*) pjsip_parse_hdr(pool, &hname,
1917
if (parsed_hdr1 == NULL) {
1918
if (test->flags & HDR_FLAG_PARSE_FAIL) {
1919
pj_pool_release(pool);
1922
PJ_LOG(3,(THIS_FILE, " error parsing header %s: %s", test->hname, test->hcontent));
1926
/* Test the parsing result */
1927
if (test->test && (rc=test->test(parsed_hdr1)) != 0) {
1928
PJ_LOG(3,(THIS_FILE, " validation failed for header %s: %s", test->hname, test->hcontent));
1929
PJ_LOG(3,(THIS_FILE, " error code is %d", rc));
1934
/* Parse with hshortname, if present */
1935
if (test->hshort_name) {
1936
hname = pj_str(test->hshort_name);
1937
len = strlen(test->hcontent);
1938
#if defined(PJSIP_UNESCAPE_IN_PLACE) && PJSIP_UNESCAPE_IN_PLACE!=0
1939
PJ_ASSERT_RETURN(len < sizeof(hcontent), PJSIP_EMSGTOOLONG);
1940
strcpy(hcontent, test->hcontent);
1942
hcontent = test->hcontent;
1945
parsed_hdr2 = (pjsip_hdr*) pjsip_parse_hdr(pool, &hname, hcontent, len, &parsed_len);
1946
if (parsed_hdr2 == NULL) {
1947
PJ_LOG(3,(THIS_FILE, " error parsing header %s: %s", test->hshort_name, test->hcontent));
1953
if (test->flags & HDR_FLAG_DONT_PRINT) {
1954
pj_pool_release(pool);
1958
/* Print the original header */
1959
input = (char*) pj_pool_alloc(pool, 1024);
1960
len = pj_ansi_snprintf(input, 1024, "%s: %s", test->hname, test->hcontent);
1961
if (len < 1 || len >= 1024)
1964
/* Print the parsed header*/
1965
output = (char*) pj_pool_alloc(pool, 1024);
1966
len = pjsip_hdr_print_on(parsed_hdr1, output, 1024);
1967
if (len < 0 || len >= 1024) {
1968
PJ_LOG(3,(THIS_FILE, " header too long: %s: %s", test->hname, test->hcontent));
1973
if (strcmp(input, output) != 0) {
1974
PJ_LOG(3,(THIS_FILE, " header character by character comparison failed."));
1975
PJ_LOG(3,(THIS_FILE, " original header=|%s|", input));
1976
PJ_LOG(3,(THIS_FILE, " parsed header =|%s|", output));
1980
pj_pool_release(pool);
1987
/*****************************************************************************/
1991
enum { COUNT = 1, DETECT=0, PARSE=1, PRINT=2 };
1997
unsigned i, max, avg_len;
2001
status = hdr_test();
2005
status = simple_test();
2006
if (status != PJ_SUCCESS)
2009
#if INCLUDE_BENCHMARKS
2010
for (i=0; i<COUNT; ++i) {
2011
PJ_LOG(3,(THIS_FILE, " benchmarking (%d of %d)..", i+1, COUNT));
2012
status = msg_benchmark(&run[i].detect, &run[i].parse, &run[i].print);
2013
if (status != PJ_SUCCESS)
2017
/* Calculate average message length */
2018
for (i=0, avg_len=0; i<PJ_ARRAY_SIZE(test_array); ++i) {
2019
avg_len += test_array[i].len;
2021
avg_len /= PJ_ARRAY_SIZE(test_array);
2024
/* Print maximum detect/sec */
2025
for (i=0, max=0; i<COUNT; ++i)
2026
if (run[i].detect > max) max = run[i].detect;
2028
PJ_LOG(3,("", " Maximum message detection/sec=%u", max));
2030
pj_ansi_sprintf(desc, "Number of SIP messages "
2031
"can be pre-parse by <tt>pjsip_find_msg()</tt> "
2032
"per second (tested with %d message sets with "
2033
"average message length of "
2034
"%d bytes)", (int)PJ_ARRAY_SIZE(test_array), avg_len);
2035
report_ival("msg-detect-per-sec", max, "msg/sec", desc);
2037
/* Print maximum parse/sec */
2038
for (i=0, max=0; i<COUNT; ++i)
2039
if (run[i].parse > max) max = run[i].parse;
2041
PJ_LOG(3,("", " Maximum message parsing/sec=%u", max));
2043
pj_ansi_sprintf(desc, "Number of SIP messages "
2044
"can be <b>parsed</b> by <tt>pjsip_parse_msg()</tt> "
2045
"per second (tested with %d message sets with "
2046
"average message length of "
2047
"%d bytes)", (int)PJ_ARRAY_SIZE(test_array), avg_len);
2048
report_ival("msg-parse-per-sec", max, "msg/sec", desc);
2050
/* Msg parsing bandwidth */
2051
report_ival("msg-parse-bandwidth-mb", avg_len*max/1000000, "MB/sec",
2052
"Message parsing bandwidth in megabytes (number of megabytes"
2053
" worth of SIP messages that can be parsed per second). "
2054
"The value is derived from msg-parse-per-sec above.");
2057
/* Print maximum print/sec */
2058
for (i=0, max=0; i<COUNT; ++i)
2059
if (run[i].print > max) max = run[i].print;
2061
PJ_LOG(3,("", " Maximum message print/sec=%u", max));
2063
pj_ansi_sprintf(desc, "Number of SIP messages "
2064
"can be <b>printed</b> by <tt>pjsip_msg_print()</tt>"
2065
" per second (tested with %d message sets with "
2066
"average message length of "
2067
"%d bytes)", (int)PJ_ARRAY_SIZE(test_array), avg_len);
2069
report_ival("msg-print-per-sec", max, "msg/sec", desc);
2071
/* Msg print bandwidth */
2072
report_ival("msg-printed-bandwidth-mb", avg_len*max/1000000, "MB/sec",
2073
"Message print bandwidth in megabytes (total size of "
2074
"SIP messages printed per second). "
2075
"The value is derived from msg-print-per-sec above.");
2077
#endif /* INCLUDE_BENCHMARKS */