blob: 06e7e27d15f32f8947adeaebac29d135bc538be6 [file] [log] [blame]
Benny Prijono5dcb38d2005-11-21 01:55:47 +00001/* $Id$ */
2/*
3 * Copyright (C) 2003-2006 Benny Prijono <benny@prijono.org>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 */
19#include "test.h"
Benny Prijono40f2f642006-01-30 18:40:05 +000020#include <pjsip.h>
Benny Prijono5dcb38d2005-11-21 01:55:47 +000021#include <pjlib.h>
22
Benny Prijono85598d92006-01-07 18:44:25 +000023#define THIS_FILE "uri_test.c"
24
Benny Prijono5dcb38d2005-11-21 01:55:47 +000025
26#define ALPHANUM "abcdefghijklmnopqrstuvwxyz" \
27 "ABCDEFGHIJKLMNOPQRSTUVWXYZ" \
28 "0123456789"
29#define MARK "-_.!~*'()"
30#define USER_CHAR ALPHANUM MARK "&=+$,;?/"
31#define PASS_CHAR ALPHANUM MARK "&=+$,"
32#define PARAM_CHAR ALPHANUM MARK "[]/:&+$"
33
Benny Prijono5b917442005-11-21 17:07:18 +000034#define POOL_SIZE 8000
Benny Prijonoe93e2872006-06-28 16:46:49 +000035#if defined(PJ_DEBUG) && PJ_DEBUG!=0
36# define LOOP_COUNT 10000
37#else
38# define LOOP_COUNT 40000
39#endif
Benny Prijono5dcb38d2005-11-21 01:55:47 +000040#define AVERAGE_URL_LEN 80
41#define THREAD_COUNT 4
42
Benny Prijonoe93e2872006-06-28 16:46:49 +000043static struct
44{
45 pj_highprec_t parse_len, print_len, cmp_len;
46 pj_timestamp parse_time, print_time, cmp_time;
47} var;
Benny Prijono5dcb38d2005-11-21 01:55:47 +000048
49
50/* URI creator functions. */
51static pjsip_uri *create_uri0( pj_pool_t *pool );
52static pjsip_uri *create_uri1( pj_pool_t *pool );
53static pjsip_uri *create_uri2( pj_pool_t *pool );
54static pjsip_uri *create_uri3( pj_pool_t *pool );
55static pjsip_uri *create_uri4( pj_pool_t *pool );
56static pjsip_uri *create_uri5( pj_pool_t *pool );
57static pjsip_uri *create_uri6( pj_pool_t *pool );
58static pjsip_uri *create_uri7( pj_pool_t *pool );
59static pjsip_uri *create_uri8( pj_pool_t *pool );
60static pjsip_uri *create_uri9( pj_pool_t *pool );
61static pjsip_uri *create_uri10( pj_pool_t *pool );
62static pjsip_uri *create_uri11( pj_pool_t *pool );
63static pjsip_uri *create_uri12( pj_pool_t *pool );
64static pjsip_uri *create_uri13( pj_pool_t *pool );
65static pjsip_uri *create_uri14( pj_pool_t *pool );
66static pjsip_uri *create_uri15( pj_pool_t *pool );
67static pjsip_uri *create_uri16( pj_pool_t *pool );
68static pjsip_uri *create_uri17( pj_pool_t *pool );
Benny Prijono82458b12005-11-23 20:56:30 +000069static pjsip_uri *create_uri25( pj_pool_t *pool );
70static pjsip_uri *create_uri26( pj_pool_t *pool );
71static pjsip_uri *create_uri27( pj_pool_t *pool );
72static pjsip_uri *create_uri28( pj_pool_t *pool );
73static pjsip_uri *create_uri29( pj_pool_t *pool );
74static pjsip_uri *create_uri30( pj_pool_t *pool );
75static pjsip_uri *create_uri31( pj_pool_t *pool );
76static pjsip_uri *create_uri32( pj_pool_t *pool );
77static pjsip_uri *create_uri33( pj_pool_t *pool );
78static pjsip_uri *create_uri34( pj_pool_t *pool );
79static pjsip_uri *create_uri35( pj_pool_t *pool );
Benny Prijono5dcb38d2005-11-21 01:55:47 +000080static pjsip_uri *create_dummy( pj_pool_t *pool );
81
82#define ERR_NOT_EQUAL -1001
83#define ERR_SYNTAX_ERR -1002
84
85struct uri_test
86{
87 pj_status_t status;
88 char str[PJSIP_MAX_URL_SIZE];
Benny Prijono82458b12005-11-23 20:56:30 +000089 pjsip_uri *(*creator)(pj_pool_t *pool);
90 const char *printed;
Benny Prijono5dcb38d2005-11-21 01:55:47 +000091 pj_size_t len;
92} uri_test_array[] =
93{
94 {
95 PJ_SUCCESS,
96 "sip:localhost",
97 &create_uri0
98 },
99 {
100 PJ_SUCCESS,
101 "sip:user@localhost",
102 &create_uri1
103 },
104 {
105 PJ_SUCCESS,
106 "sip:user:password@localhost:5060",
Benny Prijono5b917442005-11-21 17:07:18 +0000107 &create_uri2, },
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000108 {
109 /* Port is specified should not match unspecified port. */
110 ERR_NOT_EQUAL,
111 "sip:localhost:5060",
112 &create_uri3
113 },
114 {
115 /* All recognized parameters. */
116 PJ_SUCCESS,
117 "sip:localhost;transport=tcp;user=ip;ttl=255;lr;maddr=127.0.0.1;method=ACK",
118 &create_uri4
119 },
120 {
121 /* Params mixed with other params and header params. */
122 PJ_SUCCESS,
123 "sip:localhost;pickup=hurry;user=phone;message=I%20am%20sorry"
124 "?Subject=Hello%20There&Server=SIP%20Server",
125 &create_uri5
126 },
127 {
128 /* SIPS. */
129 PJ_SUCCESS,
130 "sips:localhost",
131 &create_uri6,
132 },
133 {
134 /* Name address */
135 PJ_SUCCESS,
136 "<sip:localhost>",
137 &create_uri7
138 },
139 {
140 /* Name address with display name and SIPS scheme with some redundant
141 * whitespaced.
142 */
143 PJ_SUCCESS,
144 " Power Administrator <sips:localhost>",
145 &create_uri8
146 },
147 {
148 /* Name address. */
149 PJ_SUCCESS,
150 " \"User\" <sip:user@localhost:5071>",
151 &create_uri9
152 },
153 {
154 /* Escaped sequence in display name (display=Strange User\"\\\"). */
155 PJ_SUCCESS,
156 " \"Strange User\\\"\\\\\\\"\" <sip:localhost>",
157 &create_uri10,
158 },
159 {
160 /* Errorneous escaping in display name. */
161 ERR_SYNTAX_ERR,
162 " \"Rogue User\\\" <sip:localhost>",
163 &create_uri11,
164 },
165 {
166 /* Dangling quote in display name, but that should be OK. */
167 PJ_SUCCESS,
168 "Strange User\" <sip:localhost>",
169 &create_uri12,
170 },
171 {
172 /* Special characters in parameter value must be quoted. */
173 PJ_SUCCESS,
174 "sip:localhost;pvalue=\"hello world\"",
175 &create_uri13,
176 },
177 {
178 /* Excercise strange character sets allowed in display, user, password,
179 * host, and port.
180 */
181 PJ_SUCCESS,
182 "This is -. !% *_+`'~ me <sip:a19A&=+$,;?/%2c:%40a&Zz=+$,@"
183 "my_proxy09.MY-domain.com:9801>",
184 &create_uri14,
185 },
186 {
187 /* Another excercise to the allowed character sets to the hostname. */
188 PJ_SUCCESS,
189 "sip:" ALPHANUM "-_.com",
190 &create_uri15,
191 },
192 {
193 /* Another excercise to the allowed character sets to the username
194 * and password.
195 */
196 PJ_SUCCESS,
197 "sip:" USER_CHAR ":" PASS_CHAR "@host",
198 &create_uri16,
199 },
200 {
201 /* Excercise to the pname and pvalue, and mixup of other-param
202 * between 'recognized' params.
203 */
204 PJ_SUCCESS,
205 "sip:host;user=ip;" PARAM_CHAR "%21=" PARAM_CHAR "%21"
206 ";lr;other=1;transport=sctp;other2",
207 &create_uri17,
208 },
209 {
210 /* 18: This should trigger syntax error. */
211 ERR_SYNTAX_ERR,
212 "sip:",
213 &create_dummy,
214 },
215 {
216 /* 19: Syntax error: whitespace after scheme. */
217 ERR_SYNTAX_ERR,
218 "sip :host",
219 &create_dummy,
220 },
221 {
222 /* 20: Syntax error: whitespace before hostname. */
223 ERR_SYNTAX_ERR,
224 "sip: host",
225 &create_dummy,
226 },
227 {
228 /* 21: Syntax error: invalid port. */
229 ERR_SYNTAX_ERR,
230 "sip:user:password",
231 &create_dummy,
232 },
233 {
234 /* 22: Syntax error: no host. */
235 ERR_SYNTAX_ERR,
236 "sip:user@",
237 &create_dummy,
238 },
239 {
240 /* 23: Syntax error: no user/host. */
241 ERR_SYNTAX_ERR,
242 "sip:@",
243 &create_dummy,
244 },
245 {
246 /* 24: Syntax error: empty string. */
247 ERR_SYNTAX_ERR,
248 "",
249 &create_dummy,
Benny Prijono82458b12005-11-23 20:56:30 +0000250 },
251 {
252 /* 25: Simple tel: URI with global context */
253 PJ_SUCCESS,
254 "tel:+1-201-555-0123",
255 &create_uri25,
256 "tel:+1-201-555-0123"
257 },
258 {
259 /* 26: Simple tel: URI with local context */
260 PJ_SUCCESS,
261 "tel:7042;phone-context=example.com",
262 &create_uri26,
263 "tel:7042;phone-context=example.com"
264 },
265 {
266 /* 27: Simple tel: URI with local context */
267 PJ_SUCCESS,
268 "tel:863-1234;phone-context=+1-914-555",
269 &create_uri27,
270 "tel:863-1234;phone-context=+1-914-555"
271 },
272 {
273 /* 28: Comparison between local and global number */
274 ERR_NOT_EQUAL,
275 "tel:+1",
276 &create_uri28,
277 "tel:+1"
278 },
279 {
280 /* 29: tel: with some visual chars and spaces */
281 PJ_SUCCESS,
282 "tel:(44).1234-*#+Deaf",
283 &create_uri29,
284 "tel:(44).1234-*#+Deaf"
285 },
286 {
287 /* 30: isub parameters */
288 PJ_SUCCESS,
289 "tel:+1;isub=/:@&$,-_.!~*'()[]/:&$aA1%21+=",
290 &create_uri30,
291 "tel:+1;isub=/:@&$,-_.!~*'()[]/:&$aA1%21+%3d"
292 },
293 {
294 /* 31: extension number parsing and encoding */
295 PJ_SUCCESS,
296 "tel:+1;ext=+123",
297 &create_uri31,
298 "tel:+1;ext=%2b123"
299 },
300 {
301 /* 32: context parameter parsing and encoding */
302 PJ_SUCCESS,
303 "tel:911;phone-context=+1-911",
304 &create_uri32,
305 "tel:911;phone-context=+1-911"
306 },
307 {
308 /* 33: case-insensitive comparison */
309 PJ_SUCCESS,
310 "tel:911;phone-context=emergency.example.com",
311 &create_uri33,
312 "tel:911;phone-context=emergency.example.com"
313 },
314 {
315 /* 34: parameter only appears in one URL */
316 ERR_NOT_EQUAL,
317 "tel:911;p1=p1;p2=p2",
318 &create_uri34,
319 "tel:911;p1=p1;p2=p2"
320 },
321
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000322};
323
324static pjsip_uri *create_uri0(pj_pool_t *pool)
325{
326 /* "sip:localhost" */
Benny Prijono40f2f642006-01-30 18:40:05 +0000327 pjsip_sip_uri *url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000328
329 pj_strdup2(pool, &url->host, "localhost");
330 return (pjsip_uri*)url;
331}
332
333static pjsip_uri *create_uri1(pj_pool_t *pool)
334{
335 /* "sip:user@localhost" */
Benny Prijono40f2f642006-01-30 18:40:05 +0000336 pjsip_sip_uri *url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000337
338 pj_strdup2( pool, &url->user, "user");
339 pj_strdup2( pool, &url->host, "localhost");
340
341 return (pjsip_uri*) url;
342}
343
344static pjsip_uri *create_uri2(pj_pool_t *pool)
345{
346 /* "sip:user:password@localhost:5060" */
Benny Prijono40f2f642006-01-30 18:40:05 +0000347 pjsip_sip_uri *url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000348
349 pj_strdup2( pool, &url->user, "user");
350 pj_strdup2( pool, &url->passwd, "password");
351 pj_strdup2( pool, &url->host, "localhost");
352 url->port = 5060;
353
354 return (pjsip_uri*) url;
355}
356
357static pjsip_uri *create_uri3(pj_pool_t *pool)
358{
359 /* Like: "sip:localhost:5060", but without the port. */
Benny Prijono40f2f642006-01-30 18:40:05 +0000360 pjsip_sip_uri *url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000361
362 pj_strdup2(pool, &url->host, "localhost");
363 return (pjsip_uri*)url;
364}
365
366static pjsip_uri *create_uri4(pj_pool_t *pool)
367{
368 /* "sip:localhost;transport=tcp;user=ip;ttl=255;lr;maddr=127.0.0.1;method=ACK" */
Benny Prijono40f2f642006-01-30 18:40:05 +0000369 pjsip_sip_uri *url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000370
371 pj_strdup2(pool, &url->host, "localhost");
372 pj_strdup2(pool, &url->transport_param, "tcp");
373 pj_strdup2(pool, &url->user_param, "ip");
374 url->ttl_param = 255;
375 url->lr_param = 1;
376 pj_strdup2(pool, &url->maddr_param, "127.0.0.1");
377 pj_strdup2(pool, &url->method_param, "ACK");
378
379 return (pjsip_uri*)url;
380}
381
382#define param_add(list,pname,pvalue) \
383 do { \
384 pjsip_param *param; \
385 param=pj_pool_alloc(pool, sizeof(pjsip_param)); \
386 param->name = pj_str(pname); \
387 param->value = pj_str(pvalue); \
388 pj_list_insert_before(&list, param); \
389 } while (0)
390
391static pjsip_uri *create_uri5(pj_pool_t *pool)
392{
393 /* "sip:localhost;pickup=hurry;user=phone;message=I%20am%20sorry"
394 "?Subject=Hello%20There&Server=SIP%20Server"
395 */
Benny Prijono40f2f642006-01-30 18:40:05 +0000396 pjsip_sip_uri *url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000397
398 pj_strdup2(pool, &url->host, "localhost");
399 pj_strdup2(pool, &url->user_param, "phone");
400
401 //pj_strdup2(pool, &url->other_param, ";pickup=hurry;message=I%20am%20sorry");
402 param_add(url->other_param, "pickup", "hurry");
403 param_add(url->other_param, "message", "I am sorry");
404
405 //pj_strdup2(pool, &url->header_param, "?Subject=Hello%20There&Server=SIP%20Server");
406 param_add(url->header_param, "Subject", "Hello There");
407 param_add(url->header_param, "Server", "SIP Server");
408 return (pjsip_uri*)url;
409
410}
411
412static pjsip_uri *create_uri6(pj_pool_t *pool)
413{
414 /* "sips:localhost" */
Benny Prijono40f2f642006-01-30 18:40:05 +0000415 pjsip_sip_uri *url = pjsip_sip_uri_create(pool, 1);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000416
417 pj_strdup2(pool, &url->host, "localhost");
418 return (pjsip_uri*)url;
419}
420
421static pjsip_uri *create_uri7(pj_pool_t *pool)
422{
423 /* "<sip:localhost>" */
424 pjsip_name_addr *name_addr = pjsip_name_addr_create(pool);
Benny Prijono0c2bc612006-01-10 13:31:40 +0000425 pjsip_sip_uri *url;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000426
Benny Prijono40f2f642006-01-30 18:40:05 +0000427 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000428 name_addr->uri = (pjsip_uri*) url;
429
430 pj_strdup2(pool, &url->host, "localhost");
431 return (pjsip_uri*)name_addr;
432}
433
434static pjsip_uri *create_uri8(pj_pool_t *pool)
435{
436 /* " Power Administrator <sips:localhost>" */
437 pjsip_name_addr *name_addr = pjsip_name_addr_create(pool);
Benny Prijono0c2bc612006-01-10 13:31:40 +0000438 pjsip_sip_uri *url;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000439
Benny Prijono40f2f642006-01-30 18:40:05 +0000440 url = pjsip_sip_uri_create(pool, 1);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000441 name_addr->uri = (pjsip_uri*) url;
442
443 pj_strdup2(pool, &name_addr->display, "Power Administrator");
444 pj_strdup2(pool, &url->host, "localhost");
445 return (pjsip_uri*)name_addr;
446}
447
448static pjsip_uri *create_uri9(pj_pool_t *pool)
449{
450 /* " \"User\" <sip:user@localhost:5071>" */
451 pjsip_name_addr *name_addr = pjsip_name_addr_create(pool);
Benny Prijono0c2bc612006-01-10 13:31:40 +0000452 pjsip_sip_uri *url;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000453
Benny Prijono40f2f642006-01-30 18:40:05 +0000454 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000455 name_addr->uri = (pjsip_uri*) url;
456
457 pj_strdup2(pool, &name_addr->display, "User");
458 pj_strdup2(pool, &url->user, "user");
459 pj_strdup2(pool, &url->host, "localhost");
460 url->port = 5071;
461 return (pjsip_uri*)name_addr;
462}
463
464static pjsip_uri *create_uri10(pj_pool_t *pool)
465{
466 /* " \"Strange User\\\"\\\\\\\"\" <sip:localhost>" */
467 pjsip_name_addr *name_addr = pjsip_name_addr_create(pool);
Benny Prijono0c2bc612006-01-10 13:31:40 +0000468 pjsip_sip_uri *url;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000469
Benny Prijono40f2f642006-01-30 18:40:05 +0000470 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000471 name_addr->uri = (pjsip_uri*) url;
472
473 pj_strdup2(pool, &name_addr->display, "Strange User\\\"\\\\\\\"");
474 pj_strdup2(pool, &url->host, "localhost");
475 return (pjsip_uri*)name_addr;
476}
477
478static pjsip_uri *create_uri11(pj_pool_t *pool)
479{
480 /* " \"Rogue User\\\" <sip:localhost>" */
481 pjsip_name_addr *name_addr = pjsip_name_addr_create(pool);
Benny Prijono0c2bc612006-01-10 13:31:40 +0000482 pjsip_sip_uri *url;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000483
Benny Prijono40f2f642006-01-30 18:40:05 +0000484 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000485 name_addr->uri = (pjsip_uri*) url;
486
487 pj_strdup2(pool, &name_addr->display, "Rogue User\\");
488 pj_strdup2(pool, &url->host, "localhost");
489 return (pjsip_uri*)name_addr;
490}
491
492static pjsip_uri *create_uri12(pj_pool_t *pool)
493{
494 /* "Strange User\" <sip:localhost>" */
495 pjsip_name_addr *name_addr = pjsip_name_addr_create(pool);
Benny Prijono0c2bc612006-01-10 13:31:40 +0000496 pjsip_sip_uri *url;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000497
Benny Prijono40f2f642006-01-30 18:40:05 +0000498 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000499 name_addr->uri = (pjsip_uri*) url;
500
501 pj_strdup2(pool, &name_addr->display, "Strange User\"");
502 pj_strdup2(pool, &url->host, "localhost");
503 return (pjsip_uri*)name_addr;
504}
505
506static pjsip_uri *create_uri13(pj_pool_t *pool)
507{
508 /* "sip:localhost;pvalue=\"hello world\"" */
Benny Prijono0c2bc612006-01-10 13:31:40 +0000509 pjsip_sip_uri *url;
Benny Prijono40f2f642006-01-30 18:40:05 +0000510 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000511 pj_strdup2(pool, &url->host, "localhost");
512 //pj_strdup2(pool, &url->other_param, ";pvalue=\"hello world\"");
513 param_add(url->other_param, "pvalue", "hello world");
514 return (pjsip_uri*)url;
515}
516
517static pjsip_uri *create_uri14(pj_pool_t *pool)
518{
519 /* "This is -. !% *_+`'~ me <sip:a19A&=+$,;?/%2c:%40a&Zz=+$,@my_proxy09.my-domain.com:9801>" */
520 pjsip_name_addr *name_addr = pjsip_name_addr_create(pool);
Benny Prijono0c2bc612006-01-10 13:31:40 +0000521 pjsip_sip_uri *url;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000522
Benny Prijono40f2f642006-01-30 18:40:05 +0000523 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000524 name_addr->uri = (pjsip_uri*) url;
525
526 pj_strdup2(pool, &name_addr->display, "This is -. !% *_+`'~ me");
527 pj_strdup2(pool, &url->user, "a19A&=+$,;?/,");
528 pj_strdup2(pool, &url->passwd, "@a&Zz=+$,");
529 pj_strdup2(pool, &url->host, "my_proxy09.MY-domain.com");
530 url->port = 9801;
531 return (pjsip_uri*)name_addr;
532}
533
534static pjsip_uri *create_uri15(pj_pool_t *pool)
535{
536 /* "sip:abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-_.com" */
Benny Prijono0c2bc612006-01-10 13:31:40 +0000537 pjsip_sip_uri *url;
Benny Prijono40f2f642006-01-30 18:40:05 +0000538 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000539 pj_strdup2(pool, &url->host, ALPHANUM "-_.com");
540 return (pjsip_uri*)url;
541}
542
543static pjsip_uri *create_uri16(pj_pool_t *pool)
544{
545 /* "sip:" USER_CHAR ":" PASS_CHAR "@host" */
Benny Prijono0c2bc612006-01-10 13:31:40 +0000546 pjsip_sip_uri *url;
Benny Prijono40f2f642006-01-30 18:40:05 +0000547 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000548 pj_strdup2(pool, &url->user, USER_CHAR);
549 pj_strdup2(pool, &url->passwd, PASS_CHAR);
550 pj_strdup2(pool, &url->host, "host");
551 return (pjsip_uri*)url;
552}
553
554static pjsip_uri *create_uri17(pj_pool_t *pool)
555{
556 /* "sip:host;user=ip;" PARAM_CHAR "%21=" PARAM_CHAR "%21;lr;other=1;transport=sctp;other2" */
Benny Prijono0c2bc612006-01-10 13:31:40 +0000557 pjsip_sip_uri *url;
Benny Prijono40f2f642006-01-30 18:40:05 +0000558 url = pjsip_sip_uri_create(pool, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000559 pj_strdup2(pool, &url->host, "host");
560 pj_strdup2(pool, &url->user_param, "ip");
561 pj_strdup2(pool, &url->transport_param, "sctp");
562 param_add(url->other_param, PARAM_CHAR "!", PARAM_CHAR "!");
563 param_add(url->other_param, "other", "1");
564 param_add(url->other_param, "other2", "");
565 url->lr_param = 1;
566 return (pjsip_uri*)url;
567}
568
Benny Prijono82458b12005-11-23 20:56:30 +0000569
570static pjsip_uri *create_uri25(pj_pool_t *pool)
571{
572 /* "tel:+1-201-555-0123" */
573 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
574
575 uri->number = pj_str("+1-201-555-0123");
576 return (pjsip_uri*)uri;
577}
578
579static pjsip_uri *create_uri26(pj_pool_t *pool)
580{
581 /* tel:7042;phone-context=example.com */
582 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
583
584 uri->number = pj_str("7042");
585 uri->context = pj_str("example.com");
586 return (pjsip_uri*)uri;
587}
588
589static pjsip_uri *create_uri27(pj_pool_t *pool)
590{
591 /* "tel:863-1234;phone-context=+1-914-555" */
592 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
593
594 uri->number = pj_str("863-1234");
595 uri->context = pj_str("+1-914-555");
596 return (pjsip_uri*)uri;
597}
598
599/* "tel:1" */
600static pjsip_uri *create_uri28(pj_pool_t *pool)
601{
602 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
603
604 uri->number = pj_str("1");
605 return (pjsip_uri*)uri;
606}
607
608/* "tel:(44).1234-*#+Deaf" */
609static pjsip_uri *create_uri29(pj_pool_t *pool)
610{
611 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
612
613 uri->number = pj_str("(44).1234-*#+Deaf");
614 return (pjsip_uri*)uri;
615}
616
617/* "tel:+1;isub=/:@&$,-_.!~*'()[]/:&$aA1%21+=" */
618static pjsip_uri *create_uri30(pj_pool_t *pool)
619{
620 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
621
622 uri->number = pj_str("+1");
623 uri->isub_param = pj_str("/:@&$,-_.!~*'()[]/:&$aA1%21+=");
624 return (pjsip_uri*)uri;
625}
626
627/* "tel:+1;ext=+123" */
628static pjsip_uri *create_uri31(pj_pool_t *pool)
629{
630 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
631
632 uri->number = pj_str("+1");
633 uri->ext_param = pj_str("+123");
634 return (pjsip_uri*)uri;
635}
636
637/* "tel:911;phone-context=+1-911" */
638static pjsip_uri *create_uri32(pj_pool_t *pool)
639{
640 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
641
642 uri->number = pj_str("911");
643 uri->context = pj_str("+1-911");
644 return (pjsip_uri*)uri;
645}
646
647/* "tel:911;phone-context=emergency.example.com" */
648static pjsip_uri *create_uri33(pj_pool_t *pool)
649{
650 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
651
652 uri->number = pj_str("911");
653 uri->context = pj_str("EMERGENCY.EXAMPLE.COM");
654 return (pjsip_uri*)uri;
655}
656
657/* "tel:911;p1=p1;p2=p2" */
658static pjsip_uri *create_uri34(pj_pool_t *pool)
659{
660 pjsip_tel_uri *uri = pjsip_tel_uri_create(pool);
661 pjsip_param *p;
662
663 uri->number = pj_str("911");
664
665 p = pj_pool_alloc(pool, sizeof(*p));
666 p->name = p->value = pj_str("p1");
667 pj_list_insert_before(&uri->other_param, p);
668
669 return (pjsip_uri*)uri;
670}
671
672
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000673static pjsip_uri *create_dummy(pj_pool_t *pool)
674{
675 PJ_UNUSED_ARG(pool);
676 return NULL;
677}
678
679/*****************************************************************************/
680
681/*
682 * Test one test entry.
683 */
684static pj_status_t do_uri_test(pj_pool_t *pool, struct uri_test *entry)
685{
686 pj_status_t status;
687 int len;
Benny Prijonoed76f512006-07-05 21:42:45 +0000688 char *input;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000689 pjsip_uri *parsed_uri, *ref_uri;
690 pj_str_t s1 = {NULL, 0}, s2 = {NULL, 0};
691 pj_timestamp t1, t2;
692
Benny Prijonoed76f512006-07-05 21:42:45 +0000693 if (entry->len == 0)
694 entry->len = pj_native_strlen(entry->str);
695
696#if defined(PJSIP_UNESCAPE_IN_PLACE) && PJSIP_UNESCAPE_IN_PLACE!=0
697 input = pj_pool_alloc(pool, entry->len + 1);
698 pj_memcpy(input, entry->str, entry->len);
699 input[entry->len] = '\0';
700#else
701 input = entry->str;
702#endif
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000703
704 /* Parse URI text. */
705 pj_get_timestamp(&t1);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000706 var.parse_len = var.parse_len + entry->len;
Benny Prijonoed76f512006-07-05 21:42:45 +0000707 parsed_uri = pjsip_parse_uri(pool, input, entry->len, 0);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000708 if (!parsed_uri) {
709 /* Parsing failed. If the entry says that this is expected, then
710 * return OK.
711 */
712 status = entry->status==ERR_SYNTAX_ERR ? PJ_SUCCESS : -10;
713 if (status != 0) {
Benny Prijono85598d92006-01-07 18:44:25 +0000714 PJ_LOG(3,(THIS_FILE, " uri parse error!\n"
715 " uri='%s'\n",
Benny Prijonoed76f512006-07-05 21:42:45 +0000716 input));
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000717 }
718 goto on_return;
719 }
720 pj_get_timestamp(&t2);
721 pj_sub_timestamp(&t2, &t1);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000722 pj_add_timestamp(&var.parse_time, &t2);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000723
724 /* Create the reference URI. */
725 ref_uri = entry->creator(pool);
726
727 /* Print both URI. */
728 s1.ptr = pj_pool_alloc(pool, PJSIP_MAX_URL_SIZE);
729 s2.ptr = pj_pool_alloc(pool, PJSIP_MAX_URL_SIZE);
730
731 pj_get_timestamp(&t1);
732 len = pjsip_uri_print( PJSIP_URI_IN_OTHER, parsed_uri, s1.ptr, PJSIP_MAX_URL_SIZE);
733 if (len < 1) {
734 status = -20;
735 goto on_return;
736 }
737 s1.ptr[len] = '\0';
738 s1.slen = len;
739
Benny Prijonoe93e2872006-06-28 16:46:49 +0000740 var.print_len = var.print_len + len;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000741 pj_get_timestamp(&t2);
742 pj_sub_timestamp(&t2, &t1);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000743 pj_add_timestamp(&var.print_time, &t2);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000744
745 len = pjsip_uri_print( PJSIP_URI_IN_OTHER, ref_uri, s2.ptr, PJSIP_MAX_URL_SIZE);
746 if (len < 1) {
747 status = -30;
748 goto on_return;
749 }
750 s2.ptr[len] = '\0';
751 s2.slen = len;
752
753 /* Full comparison of parsed URI with reference URI. */
Benny Prijono5b917442005-11-21 17:07:18 +0000754 pj_get_timestamp(&t1);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000755 status = pjsip_uri_cmp(PJSIP_URI_IN_OTHER, parsed_uri, ref_uri);
756 if (status != 0) {
757 /* Not equal. See if this is the expected status. */
758 status = entry->status==ERR_NOT_EQUAL ? PJ_SUCCESS : -40;
759 if (status != 0) {
Benny Prijono85598d92006-01-07 18:44:25 +0000760 PJ_LOG(3,(THIS_FILE, " uri comparison mismatch, status=%d:\n"
761 " uri1='%s'\n"
762 " uri2='%s'",
763 status, s1.ptr, s2.ptr));
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000764 }
765 goto on_return;
766
767 } else {
768 /* Equal. See if this is the expected status. */
769 status = entry->status==PJ_SUCCESS ? PJ_SUCCESS : -50;
770 if (status != PJ_SUCCESS) {
771 goto on_return;
772 }
773 }
774
Benny Prijonoe93e2872006-06-28 16:46:49 +0000775 var.cmp_len = var.cmp_len + len;
Benny Prijono5b917442005-11-21 17:07:18 +0000776 pj_get_timestamp(&t2);
777 pj_sub_timestamp(&t2, &t1);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000778 pj_add_timestamp(&var.cmp_time, &t2);
Benny Prijono5b917442005-11-21 17:07:18 +0000779
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000780 /* Compare text. */
Benny Prijono82458b12005-11-23 20:56:30 +0000781 if (entry->printed) {
782 if (pj_strcmp2(&s1, entry->printed) != 0) {
783 /* Not equal. */
Benny Prijono85598d92006-01-07 18:44:25 +0000784 PJ_LOG(3,(THIS_FILE, " uri print mismatch:\n"
785 " printed='%s'\n"
786 " expectd='%s'",
787 s1.ptr, entry->printed));
Benny Prijono82458b12005-11-23 20:56:30 +0000788 status = -60;
789 }
790 } else {
791 if (pj_strcmp(&s1, &s2) != 0) {
792 /* Not equal. */
Benny Prijono85598d92006-01-07 18:44:25 +0000793 PJ_LOG(3,(THIS_FILE, " uri print mismatch:\n"
794 " uri1='%s'\n"
795 " uri2='%s'",
796 s1.ptr, s2.ptr));
Benny Prijono82458b12005-11-23 20:56:30 +0000797 status = -70;
798 }
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000799 }
800
801on_return:
802 return status;
803}
804
Benny Prijonoe93e2872006-06-28 16:46:49 +0000805
806static int simple_uri_test(void)
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000807{
Benny Prijonoe93e2872006-06-28 16:46:49 +0000808 unsigned i;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000809 pj_pool_t *pool;
810 pj_status_t status;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000811
Benny Prijono85598d92006-01-07 18:44:25 +0000812 PJ_LOG(3,(THIS_FILE, " simple test"));
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000813 for (i=0; i<PJ_ARRAY_SIZE(uri_test_array); ++i) {
Benny Prijono95c63482006-07-06 14:28:45 +0000814 pool = pjsip_endpt_create_pool(endpt, "", POOL_SIZE, POOL_SIZE);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000815 status = do_uri_test(pool, &uri_test_array[i]);
Benny Prijono95c63482006-07-06 14:28:45 +0000816 pjsip_endpt_release_pool(endpt, pool);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000817 if (status != PJ_SUCCESS) {
Benny Prijono85598d92006-01-07 18:44:25 +0000818 PJ_LOG(3,(THIS_FILE, " error %d when testing entry %d",
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000819 status, i));
Benny Prijonoe93e2872006-06-28 16:46:49 +0000820 return status;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000821 }
822 }
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000823
Benny Prijonoe93e2872006-06-28 16:46:49 +0000824 return 0;
825}
826
827static int uri_benchmark(unsigned *p_parse, unsigned *p_print, unsigned *p_cmp)
828{
829 unsigned i, loop;
Benny Prijonoe93e2872006-06-28 16:46:49 +0000830 pj_status_t status;
831 pj_timestamp zero;
832 pj_time_val elapsed;
833 pj_highprec_t avg_parse, avg_print, avg_cmp, kbytes;
834
Benny Prijonoac623b32006-07-03 15:19:31 +0000835 pj_bzero(&var, sizeof(var));
Benny Prijonoe93e2872006-06-28 16:46:49 +0000836
837 zero.u32.hi = zero.u32.lo = 0;
838
839 var.parse_len = var.print_len = var.cmp_len = 0;
840 var.parse_time.u32.hi = var.parse_time.u32.lo = 0;
841 var.print_time.u32.hi = var.print_time.u32.lo = 0;
842 var.cmp_time.u32.hi = var.cmp_time.u32.lo = 0;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000843 for (loop=0; loop<LOOP_COUNT; ++loop) {
844 for (i=0; i<PJ_ARRAY_SIZE(uri_test_array); ++i) {
Benny Prijono95c63482006-07-06 14:28:45 +0000845 pj_pool_t *pool;
846 pool = pjsip_endpt_create_pool(endpt, "", POOL_SIZE, POOL_SIZE);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000847 status = do_uri_test(pool, &uri_test_array[i]);
Benny Prijono95c63482006-07-06 14:28:45 +0000848 pjsip_endpt_release_pool(endpt, pool);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000849 if (status != PJ_SUCCESS) {
Benny Prijono85598d92006-01-07 18:44:25 +0000850 PJ_LOG(3,(THIS_FILE, " error %d when testing entry %d",
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000851 status, i));
Benny Prijonofa73e3e2006-01-05 23:35:46 +0000852 pjsip_endpt_release_pool(endpt, pool);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000853 goto on_return;
854 }
855 }
856 }
857
Benny Prijonoe93e2872006-06-28 16:46:49 +0000858 kbytes = var.parse_len;
Benny Prijono5b917442005-11-21 17:07:18 +0000859 pj_highprec_mod(kbytes, 1000000);
860 pj_highprec_div(kbytes, 100000);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000861 elapsed = pj_elapsed_time(&zero, &var.parse_time);
862 avg_parse = pj_elapsed_usec(&zero, &var.parse_time);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000863 pj_highprec_mul(avg_parse, AVERAGE_URL_LEN);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000864 pj_highprec_div(avg_parse, var.parse_len);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000865 avg_parse = 1000000 / avg_parse;
866
Benny Prijono85598d92006-01-07 18:44:25 +0000867 PJ_LOG(3,(THIS_FILE,
868 " %u.%u MB of urls parsed in %d.%03ds (avg=%d urls/sec)",
Benny Prijonoe93e2872006-06-28 16:46:49 +0000869 (unsigned)(var.parse_len/1000000), (unsigned)kbytes,
Benny Prijono85598d92006-01-07 18:44:25 +0000870 elapsed.sec, elapsed.msec,
871 (unsigned)avg_parse));
Benny Prijono5b917442005-11-21 17:07:18 +0000872
Benny Prijonoe93e2872006-06-28 16:46:49 +0000873 *p_parse = (unsigned)avg_parse;
874
875 kbytes = var.print_len;
Benny Prijono5b917442005-11-21 17:07:18 +0000876 pj_highprec_mod(kbytes, 1000000);
877 pj_highprec_div(kbytes, 100000);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000878 elapsed = pj_elapsed_time(&zero, &var.print_time);
879 avg_print = pj_elapsed_usec(&zero, &var.print_time);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000880 pj_highprec_mul(avg_print, AVERAGE_URL_LEN);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000881 pj_highprec_div(avg_print, var.parse_len);
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000882 avg_print = 1000000 / avg_print;
883
Benny Prijono85598d92006-01-07 18:44:25 +0000884 PJ_LOG(3,(THIS_FILE,
885 " %u.%u MB of urls printed in %d.%03ds (avg=%d urls/sec)",
Benny Prijonoe93e2872006-06-28 16:46:49 +0000886 (unsigned)(var.print_len/1000000), (unsigned)kbytes,
Benny Prijono85598d92006-01-07 18:44:25 +0000887 elapsed.sec, elapsed.msec,
888 (unsigned)avg_print));
Benny Prijono5b917442005-11-21 17:07:18 +0000889
Benny Prijonoe93e2872006-06-28 16:46:49 +0000890 *p_print = (unsigned)avg_print;
891
892 kbytes = var.cmp_len;
Benny Prijono5b917442005-11-21 17:07:18 +0000893 pj_highprec_mod(kbytes, 1000000);
894 pj_highprec_div(kbytes, 100000);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000895 elapsed = pj_elapsed_time(&zero, &var.cmp_time);
896 avg_cmp = pj_elapsed_usec(&zero, &var.cmp_time);
Benny Prijono5b917442005-11-21 17:07:18 +0000897 pj_highprec_mul(avg_cmp, AVERAGE_URL_LEN);
Benny Prijonoe93e2872006-06-28 16:46:49 +0000898 pj_highprec_div(avg_cmp, var.cmp_len);
Benny Prijono5b917442005-11-21 17:07:18 +0000899 avg_cmp = 1000000 / avg_cmp;
900
Benny Prijono85598d92006-01-07 18:44:25 +0000901 PJ_LOG(3,(THIS_FILE,
902 " %u.%u MB of urls compared in %d.%03ds (avg=%d urls/sec)",
Benny Prijonoe93e2872006-06-28 16:46:49 +0000903 (unsigned)(var.cmp_len/1000000), (unsigned)kbytes,
Benny Prijono85598d92006-01-07 18:44:25 +0000904 elapsed.sec, elapsed.msec,
905 (unsigned)avg_cmp));
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000906
Benny Prijonoe93e2872006-06-28 16:46:49 +0000907 *p_cmp = (unsigned)avg_cmp;
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000908
909on_return:
Benny Prijono5dcb38d2005-11-21 01:55:47 +0000910 return status;
911}
912
Benny Prijonoe93e2872006-06-28 16:46:49 +0000913
914/*****************************************************************************/
915
916int uri_test(void)
917{
918 enum { COUNT = 4, DETECT=0, PARSE=1, PRINT=2 };
919 struct {
920 unsigned parse;
921 unsigned print;
922 unsigned cmp;
923 } run[COUNT];
924 unsigned i, max, avg_len;
925 char desc[200];
926 pj_status_t status;
927
928 status = simple_uri_test();
929 if (status != PJ_SUCCESS)
930 return status;
931
932 for (i=0; i<COUNT; ++i) {
933 PJ_LOG(3,(THIS_FILE, " benchmarking (%d of %d)...", i+1, COUNT));
934 status = uri_benchmark(&run[i].parse, &run[i].print, &run[i].cmp);
935 if (status != PJ_SUCCESS)
936 return status;
937 }
938
939 /* Calculate average URI length */
940 for (i=0, avg_len=0; i<PJ_ARRAY_SIZE(uri_test_array); ++i) {
941 avg_len += uri_test_array[i].len;
942 }
943 avg_len /= PJ_ARRAY_SIZE(uri_test_array);
944
945
946 /*
947 * Print maximum parse/sec
948 */
949 for (i=0, max=0; i<COUNT; ++i)
950 if (run[i].parse > max) max = run[i].parse;
951
952 PJ_LOG(3,("", " Maximum URI parse/sec=%u", max));
953
954 pj_ansi_sprintf(desc, "Number of SIP/TEL URIs that can be <B>parsed</B> with "
955 "<tt>pjsip_parse_uri()</tt> per second "
956 "(tested with %d URI set, with average length of "
957 "%d chars)",
958 PJ_ARRAY_SIZE(uri_test_array), avg_len);
959
960 report_ival("uri-parse-per-sec", max, "URI/sec", desc);
961
962 /* URI parsing bandwidth */
963 report_ival("uri-parse-bandwidth-mb", avg_len*max/1000000, "MB/sec",
964 "URI parsing bandwidth in megabytes (number of megabytes "
965 "worth of URI that can be parsed per second)");
966
967
968 /* Print maximum print/sec */
969 for (i=0, max=0; i<COUNT; ++i)
970 if (run[i].print > max) max = run[i].print;
971
972 PJ_LOG(3,("", " Maximum URI print/sec=%u", max));
973
974 pj_ansi_sprintf(desc, "Number of SIP/TEL URIs that can be <B>printed</B> with "
975 "<tt>pjsip_uri_print()</tt> per second "
976 "(tested with %d URI set, with average length of "
977 "%d chars)",
978 PJ_ARRAY_SIZE(uri_test_array), avg_len);
979
980 report_ival("uri-print-per-sec", max, "URI/sec", desc);
981
982 /* Print maximum detect/sec */
983 for (i=0, max=0; i<COUNT; ++i)
984 if (run[i].cmp > max) max = run[i].cmp;
985
986 PJ_LOG(3,("", " Maximum URI comparison/sec=%u", max));
987
988 pj_ansi_sprintf(desc, "Number of SIP/TEL URIs that can be <B>compared</B> with "
989 "<tt>pjsip_uri_cmp()</tt> per second "
990 "(tested with %d URI set, with average length of "
991 "%d chars)",
992 PJ_ARRAY_SIZE(uri_test_array), avg_len);
993
994 report_ival("uri-cmp-per-sec", max, "URI/sec", desc);
995
996 return PJ_SUCCESS;
997}
998