Ignore:
Timestamp:
Nov 11, 2005 7:01:31 PM (18 years ago)
Author:
bennylp
Message:

First clean compile of pjsip

File:
1 edited

Legend:

Unmodified
Added
Removed
  • pjproject/main/pjsip/src/pjsip/sip_parser.c

    • Property svn:keywords set to Id
    r3 r43  
    11/* $Id$ 
    2  * 
    32 */ 
    43#include <pjsip/sip_parser.h> 
     
    65#include <pjsip/sip_msg.h> 
    76#include <pjsip/sip_auth_parser.h> 
    8 #include <pj/scanner.h> 
     7#include <pjsip/sip_errno.h> 
     8#include <pjsip/sip_transport.h>        /* rdata structure */ 
     9#include <pjlib-util/scanner.h> 
    910#include <pj/except.h> 
    1011#include <pj/log.h> 
     
    1314#include <pj/pool.h> 
    1415#include <pj/string.h> 
    15 #include <ctype.h>      /* tolower() */ 
     16#include <pj/ctype.h> 
     17#include <pj/assert.h> 
    1618 
    1719#define RESERVED    ";/?:@&=+$," 
     
    2022#define USER        "&=+$,;?/" 
    2123#define PASS        "&=+$," 
    22 #define TOKEN       "-.!%*_=`'~+"   /* '+' is because of application/pidf+xml in Content-Type! */ 
     24#define TOKEN       "-.!%*_=`'~+"   /* '+' is because of application/pidf+xml 
     25                                     * in Content-Type! */ 
    2326#define HOST        "_-." 
    2427#define HEX_DIGIT   "abcdefABCDEF" 
     
    4649 * Global vars (also extern). 
    4750 */ 
    48 const pj_str_t  pjsip_USER_STR = { "user", 4}; 
    49 const pj_str_t  pjsip_METHOD_STR = { "method", 6}; 
     51const pj_str_t  pjsip_USER_STR      = { "user", 4}; 
     52const pj_str_t  pjsip_METHOD_STR    = { "method", 6}; 
    5053const pj_str_t  pjsip_TRANSPORT_STR = { "transport", 9}; 
    51 const pj_str_t  pjsip_MADDR_STR = { "maddr", 5 }; 
    52 const pj_str_t  pjsip_LR_STR = { "lr", 2 }; 
    53 const pj_str_t  pjsip_SIP_STR = { "sip", 3 }; 
    54 const pj_str_t  pjsip_SIPS_STR = { "sips", 4 }; 
    55 const pj_str_t  pjsip_TEL_STR = { "tel", 3 }; 
    56 const pj_str_t  pjsip_BRANCH_STR = { "branch", 6 }; 
    57 const pj_str_t  pjsip_TTL_STR = { "ttl", 3 }; 
    58 const pj_str_t  pjsip_PNAME_STR = { "received", 8 }; 
    59 const pj_str_t  pjsip_Q_STR = { "q", 1 }; 
    60 const pj_str_t  pjsip_EXPIRES_STR = { "expires", 7 }; 
    61 const pj_str_t  pjsip_TAG_STR = { "tag", 3 }; 
    62 const pj_str_t  pjsip_RPORT_STR = { "rport", 5}; 
    63  
    64 pj_char_spec    pjsip_HOST_SPEC,            /* For scanning host part. */ 
    65                 pjsip_DIGIT_SPEC,           /* Decimal digits */ 
    66                 pjsip_ALPHA_SPEC,           /* Alpha (A-Z, a-z) */ 
    67                 pjsip_ALNUM_SPEC,           /* Decimal + Alpha. */ 
    68                 pjsip_TOKEN_SPEC,           /* Token. */ 
    69                 pjsip_HEX_SPEC,             /* Hexadecimal digits. */ 
    70                 pjsip_PARAM_CHAR_SPEC,      /* For scanning pname (or pvalue when it's not quoted.) */ 
    71                 pjsip_PROBE_USER_HOST_SPEC, /* Hostname characters. */ 
    72                 pjsip_PASSWD_SPEC,          /* Password. */ 
    73                 pjsip_USER_SPEC,            /* User */ 
    74                 pjsip_ARRAY_ELEMENTS,       /* Array separator. */ 
    75                 pjsip_NEWLINE_OR_EOF_SPEC,  /* For eating up header.*/ 
    76                 pjsip_DISPLAY_SCAN_SPEC;    /* Used when searching for display name in URL. */ 
     54const pj_str_t  pjsip_MADDR_STR     = { "maddr", 5 }; 
     55const pj_str_t  pjsip_LR_STR        = { "lr", 2 }; 
     56const pj_str_t  pjsip_SIP_STR       = { "sip", 3 }; 
     57const pj_str_t  pjsip_SIPS_STR      = { "sips", 4 }; 
     58const pj_str_t  pjsip_TEL_STR       = { "tel", 3 }; 
     59const pj_str_t  pjsip_BRANCH_STR    = { "branch", 6 }; 
     60const pj_str_t  pjsip_TTL_STR       = { "ttl", 3 }; 
     61const pj_str_t  pjsip_PNAME_STR     = { "received", 8 }; 
     62const pj_str_t  pjsip_Q_STR         = { "q", 1 }; 
     63const pj_str_t  pjsip_EXPIRES_STR   = { "expires", 7 }; 
     64const pj_str_t  pjsip_TAG_STR       = { "tag", 3 }; 
     65const pj_str_t  pjsip_RPORT_STR     = { "rport", 5}; 
     66 
     67/* Character Input Specification buffer. */ 
     68static pj_cis_buf_t cis_buf; 
     69 
     70/* Character Input Specifications. */ 
     71pj_cis_t    pjsip_HOST_SPEC,            /* For scanning host part. */ 
     72            pjsip_DIGIT_SPEC,           /* Decimal digits */ 
     73            pjsip_ALPHA_SPEC,           /* Alpha (A-Z, a-z) */ 
     74            pjsip_ALNUM_SPEC,           /* Decimal + Alpha. */ 
     75            pjsip_TOKEN_SPEC,           /* Token. */ 
     76            pjsip_HEX_SPEC,             /* Hexadecimal digits. */ 
     77            pjsip_PARAM_CHAR_SPEC,      /* For scanning pname (or pvalue when 
     78                                         * it's not quoted.) */ 
     79            pjsip_PROBE_USER_HOST_SPEC, /* Hostname characters. */ 
     80            pjsip_PASSWD_SPEC,          /* Password. */ 
     81            pjsip_USER_SPEC,            /* User */ 
     82            pjsip_ARRAY_ELEMENTS,       /* Array separator. */ 
     83            pjsip_NEWLINE_OR_EOF_SPEC,  /* For eating up header.*/ 
     84            pjsip_DISPLAY_SCAN_SPEC;    /* Used when searching for display name 
     85                                         * in URL. */ 
    7786 
    7887 
     
    8089 * Forward decl. 
    8190 */ 
    82 static pjsip_msg *        int_parse_msg( pj_scanner *scanner,  
    83                                          pj_pool_t *pool,  
    84                                          pjsip_parser_err_report *err_list); 
    85 static void               int_parse_param( pj_scanner *scanner,  
    86                                            pj_str_t *pname,  
    87                                            pj_str_t *pvalue); 
    88 static void               int_parse_req_line( pj_scanner *scanner,  
    89                                               pj_pool_t *pool, 
    90                                               pjsip_request_line *req_line); 
    91 static int                int_is_next_user( pj_scanner *scanner); 
    92 static void               int_parse_status_line( pj_scanner *scanner,  
    93                                                  pjsip_status_line *line); 
    94 static void               int_parse_user_pass( pj_scanner *scanner,  
    95                                                pj_str_t *user,  
    96                                                pj_str_t *pass); 
    97 static void               int_parse_uri_host_port( pj_scanner *scanner,  
    98                                                    pj_str_t *p_host,  
    99                                                    int *p_port); 
    100 static pjsip_uri *        int_parse_uri_or_name_addr( pj_scanner *scanner,  
    101                                             pj_pool_t *pool, unsigned option); 
    102 static pjsip_url *        int_parse_sip_url( pj_scanner *scanner,  
    103                                              pj_pool_t *pool, 
    104                                              pj_bool_t parse_params); 
    105 static pjsip_name_addr*   int_parse_name_addr( pj_scanner *scanner,  
    106                                                pj_pool_t *pool ); 
    107 static void               parse_hdr_end( pj_scanner *scanner ); 
    108 static pjsip_accept_hdr*  parse_hdr_accept( pj_scanner *scanner,  
    109                                             pj_pool_t *pool); 
    110 static pjsip_allow_hdr*   parse_hdr_allow( pj_scanner *scanner,  
    111                                            pj_pool_t *pool); 
    112 static pjsip_cid_hdr*     parse_hdr_call_id( pj_scanner *scanner,  
    113                                              pj_pool_t *pool); 
    114 static pjsip_contact_hdr* parse_hdr_contact( pj_scanner *scanner,  
    115                                              pj_pool_t *pool); 
    116 static pjsip_clen_hdr*    parse_hdr_content_length( pj_scanner *scanner,  
    117                                                     pj_pool_t *pool); 
    118 static pjsip_ctype_hdr*   parse_hdr_content_type( pj_scanner *scanner,  
    119                                                   pj_pool_t *pool); 
    120 static pjsip_cseq_hdr*    parse_hdr_cseq( pj_scanner *scanner,  
    121                                           pj_pool_t *pool); 
    122 static pjsip_expires_hdr* parse_hdr_expires( pj_scanner *scanner,  
    123                                           pj_pool_t *pool); 
    124 static pjsip_from_hdr*    parse_hdr_from( pj_scanner *scanner,  
    125                                           pj_pool_t *pool); 
    126 static pjsip_max_forwards_hdr*  parse_hdr_max_forwards( pj_scanner *scanner,  
    127                                         pj_pool_t *pool); 
    128 static pjsip_min_expires_hdr*  parse_hdr_min_expires( pj_scanner *scanner,  
    129                                         pj_pool_t *pool); 
    130 static pjsip_rr_hdr*      parse_hdr_rr( pj_scanner *scanner,  
    131                                         pj_pool_t *pool); 
    132 static pjsip_route_hdr*   parse_hdr_route( pj_scanner *scanner,  
    133                                            pj_pool_t *pool); 
    134 static pjsip_require_hdr* parse_hdr_require( pj_scanner *scanner,  
    135                                         pj_pool_t *pool); 
    136 static pjsip_retry_after_hdr* parse_hdr_retry_after( pj_scanner *scanner,  
    137                                         pj_pool_t *pool); 
    138 static pjsip_supported_hdr* parse_hdr_supported( pj_scanner *scanner,  
    139                                         pj_pool_t *pool); 
    140 static pjsip_to_hdr*      parse_hdr_to( pj_scanner *scanner,  
    141                                         pj_pool_t *pool); 
    142 static pjsip_unsupported_hdr* parse_hdr_unsupported( pj_scanner *scanner,  
    143                                         pj_pool_t *pool); 
    144 static pjsip_via_hdr*     parse_hdr_via( pj_scanner *scanner,  
    145                                          pj_pool_t *pool); 
    146 static pjsip_generic_string_hdr* parse_hdr_generic_string( pj_scanner *scanner,  
    147                                              pj_pool_t *pool); 
     91static pjsip_msg *  int_parse_msg( pjsip_parse_ctx *ctx,  
     92                                   pjsip_parser_err_report *err_list); 
     93static void         int_parse_param( pj_scanner *scanner,  
     94                                     pj_str_t *pname,  
     95                                     pj_str_t *pvalue); 
     96static void         int_parse_req_line( pj_scanner *scanner,  
     97                                        pj_pool_t *pool, 
     98                                        pjsip_request_line *req_line); 
     99static int          int_is_next_user( pj_scanner *scanner); 
     100static void         int_parse_status_line( pj_scanner *scanner,  
     101                                           pjsip_status_line *line); 
     102static void         int_parse_user_pass( pj_scanner *scanner,  
     103                                         pj_str_t *user,  
     104                                         pj_str_t *pass); 
     105static void         int_parse_uri_host_port( pj_scanner *scanner,  
     106                                             pj_str_t *p_host,  
     107                                             int *p_port); 
     108static pjsip_uri *  int_parse_uri_or_name_addr( pj_scanner *scanner,  
     109                                                pj_pool_t *pool,  
     110                                                unsigned option); 
     111static pjsip_url *  int_parse_sip_url( pj_scanner *scanner,  
     112                                       pj_pool_t *pool, 
     113                                       pj_bool_t parse_params); 
     114static pjsip_name_addr * 
     115                    int_parse_name_addr( pj_scanner *scanner,  
     116                                         pj_pool_t *pool ); 
     117static void         parse_hdr_end( pj_scanner *scanner ); 
     118 
     119static pjsip_hdr*   parse_hdr_accept( pjsip_parse_ctx *ctx ); 
     120static pjsip_hdr*   parse_hdr_allow( pjsip_parse_ctx *ctx ); 
     121static pjsip_hdr*   parse_hdr_call_id( pjsip_parse_ctx *ctx); 
     122static pjsip_hdr*   parse_hdr_contact( pjsip_parse_ctx *ctx); 
     123static pjsip_hdr*   parse_hdr_content_len( pjsip_parse_ctx *ctx ); 
     124static pjsip_hdr*   parse_hdr_content_type( pjsip_parse_ctx *ctx ); 
     125static pjsip_hdr*   parse_hdr_cseq( pjsip_parse_ctx *ctx ); 
     126static pjsip_hdr*   parse_hdr_expires( pjsip_parse_ctx *ctx ); 
     127static pjsip_hdr*   parse_hdr_from( pjsip_parse_ctx *ctx ); 
     128static pjsip_hdr*   parse_hdr_max_forwards( pjsip_parse_ctx *ctx); 
     129static pjsip_hdr*   parse_hdr_min_expires( pjsip_parse_ctx *ctx ); 
     130static pjsip_hdr*   parse_hdr_rr( pjsip_parse_ctx *ctx ); 
     131static pjsip_hdr*   parse_hdr_route( pjsip_parse_ctx *ctx ); 
     132static pjsip_hdr*   parse_hdr_require( pjsip_parse_ctx *ctx ); 
     133static pjsip_hdr*   parse_hdr_retry_after( pjsip_parse_ctx *ctx ); 
     134static pjsip_hdr*   parse_hdr_supported( pjsip_parse_ctx *ctx ); 
     135static pjsip_hdr*   parse_hdr_to( pjsip_parse_ctx *ctx ); 
     136static pjsip_hdr*   parse_hdr_unsupported( pjsip_parse_ctx *ctx ); 
     137static pjsip_hdr*   parse_hdr_via( pjsip_parse_ctx *ctx ); 
     138static pjsip_hdr*   parse_hdr_generic_string( pjsip_parse_ctx *ctx); 
    148139 
    149140/* Convert non NULL terminated string to integer. */ 
    150 static unsigned long pj_strtoul_mindigit(const pj_str_t *str, unsigned mindig) 
     141static unsigned long pj_strtoul_mindigit(const pj_str_t *str,  
     142                                         unsigned mindig) 
    151143{ 
    152144    unsigned long value; 
     
    164156 
    165157/* Case insensitive comparison */ 
    166 #define parser_stricmp(str1, str2)  \ 
    167             (str1.slen != str2.slen ? -1 : \ 
    168                 !(memcmp(str1.ptr, str2.ptr, str1.slen)==0 || stricmp(str1.ptr, str2.ptr)==0)) 
     158#define parser_stricmp(str1, str2)  pj_stricmp(&str1, &str2) 
     159 
    169160 
    170161/* Syntax error handler for parser. */ 
    171162static void on_syntax_error(pj_scanner *scanner) 
    172163{ 
    173     PJ_UNUSED_ARG(scanner) 
     164    PJ_UNUSED_ARG(scanner); 
    174165    PJ_THROW(PJSIP_SYN_ERR_EXCEPTION); 
    175166} 
     
    177168/* Concatenate unrecognized params into single string. */ 
    178169void pjsip_concat_param_imp( pj_str_t *param, pj_pool_t *pool,  
    179                              const pj_str_t *pname, const pj_str_t *pvalue, int sepchar) 
     170                             const pj_str_t *pname, const pj_str_t *pvalue,  
     171                             int sepchar) 
    180172{ 
    181173    char *new_param, *p; 
     
    214206 
    215207/* Initialize static properties of the parser. */ 
    216 static void init_parser() 
     208static pj_status_t init_parser() 
    217209{ 
    218210    static int initialized; 
     211    pj_status_t status; 
    219212 
    220213    if (initialized) 
    221         return; 
     214        return PJ_SUCCESS; 
    222215 
    223216    initialized = 1; 
    224217 
    225     pj_cs_add_num( pjsip_DIGIT_SPEC ); 
    226     pj_cs_add_alpha( pjsip_ALPHA_SPEC ); 
     218    pj_cis_buf_init(&cis_buf); 
     219 
     220    status = pj_cis_init(&cis_buf, &pjsip_DIGIT_SPEC); 
     221    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     222    pj_cis_add_num(&pjsip_DIGIT_SPEC); 
    227223     
    228     pj_cs_add_alpha( pjsip_ALNUM_SPEC ); 
    229     pj_cs_add_num( pjsip_ALNUM_SPEC ); 
    230  
    231     pj_cs_add_str(pjsip_NEWLINE_OR_EOF_SPEC, "\r\n"); 
     224    status = pj_cis_init(&cis_buf, &pjsip_ALPHA_SPEC); 
     225    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     226    pj_cis_add_alpha( &pjsip_ALPHA_SPEC ); 
     227     
     228    status = pj_cis_init(&cis_buf, &pjsip_ALNUM_SPEC); 
     229    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     230    pj_cis_add_alpha( &pjsip_ALNUM_SPEC ); 
     231    pj_cis_add_num( &pjsip_ALNUM_SPEC ); 
     232 
     233    status = pj_cis_init(&cis_buf, &pjsip_NEWLINE_OR_EOF_SPEC); 
     234    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     235    pj_cis_add_str(&pjsip_NEWLINE_OR_EOF_SPEC, "\r\n"); 
    232236    //pj_cs_set(pjsip_NEWLINE_OR_EOF_SPEC, 0); 
    233237 
    234     pj_cs_add_str( pjsip_ARRAY_ELEMENTS, ",\r\n"); 
    235  
    236     pj_memcpy(pjsip_TOKEN_SPEC, pjsip_ALNUM_SPEC, sizeof(pj_char_spec)); 
    237     pj_cs_add_str( pjsip_TOKEN_SPEC, TOKEN); 
    238  
    239     pj_memcpy(pjsip_HOST_SPEC, pjsip_ALNUM_SPEC, sizeof(pj_char_spec)); 
    240     pj_cs_add_str( pjsip_HOST_SPEC, HOST); 
    241  
    242     pj_memcpy(pjsip_HEX_SPEC, pjsip_DIGIT_SPEC, sizeof(pj_char_spec)); 
    243     pj_cs_add_str( pjsip_HEX_SPEC, HEX_DIGIT); 
    244  
    245     pj_memcpy(pjsip_PARAM_CHAR_SPEC, pjsip_ALNUM_SPEC, sizeof(pj_char_spec)); 
    246     pj_cs_add_str( pjsip_PARAM_CHAR_SPEC, PARAM_CHAR); 
    247  
    248     pj_memcpy(pjsip_USER_SPEC, pjsip_ALNUM_SPEC, sizeof(pj_char_spec)); 
    249     pj_cs_add_str( pjsip_USER_SPEC, MARK ESCAPED USER ); 
    250  
    251     pj_memcpy(pjsip_PASSWD_SPEC, pjsip_ALNUM_SPEC, sizeof(pj_char_spec)); 
    252     pj_cs_add_str( pjsip_PASSWD_SPEC, MARK ESCAPED PASS); 
    253  
    254     pj_cs_add_str( pjsip_PROBE_USER_HOST_SPEC, "@ \n>"); 
    255     pj_cs_invert( pjsip_PROBE_USER_HOST_SPEC ); 
    256  
    257     pj_cs_add_str( pjsip_DISPLAY_SCAN_SPEC, ":\r\n<"); 
    258  
    259     pjsip_register_hdr_parser( "Accept", NULL, (pjsip_parse_hdr_func*) &parse_hdr_accept); 
    260     pjsip_register_hdr_parser( "Allow", NULL, (pjsip_parse_hdr_func*) &parse_hdr_allow); 
    261     pjsip_register_hdr_parser( "Call-ID", NULL, (pjsip_parse_hdr_func*) &parse_hdr_call_id); 
    262     pjsip_register_hdr_parser( "Contact", "m", (pjsip_parse_hdr_func*) &parse_hdr_contact); 
    263     pjsip_register_hdr_parser( "Content-Length", NULL, (pjsip_parse_hdr_func*) &parse_hdr_content_length); 
    264     pjsip_register_hdr_parser( "Content-Type", NULL, (pjsip_parse_hdr_func*) &parse_hdr_content_type); 
    265     pjsip_register_hdr_parser( "CSeq", NULL, (pjsip_parse_hdr_func*) &parse_hdr_cseq); 
    266     pjsip_register_hdr_parser( "Expires", NULL, (pjsip_parse_hdr_func*) &parse_hdr_expires); 
    267     pjsip_register_hdr_parser( "From", "f", (pjsip_parse_hdr_func*) &parse_hdr_from); 
    268     pjsip_register_hdr_parser( "Max-Forwards", NULL, (pjsip_parse_hdr_func*) &parse_hdr_max_forwards); 
    269     pjsip_register_hdr_parser( "Min-Expires", NULL, (pjsip_parse_hdr_func*) &parse_hdr_min_expires); 
    270     pjsip_register_hdr_parser( "Record-Route", NULL, (pjsip_parse_hdr_func*) &parse_hdr_rr); 
    271     pjsip_register_hdr_parser( "Route", NULL, (pjsip_parse_hdr_func*) &parse_hdr_route); 
    272     pjsip_register_hdr_parser( "Require", NULL, (pjsip_parse_hdr_func*) &parse_hdr_require); 
    273     pjsip_register_hdr_parser( "Retry-After", NULL, (pjsip_parse_hdr_func*) &parse_hdr_retry_after); 
    274     pjsip_register_hdr_parser( "Supported", "k", (pjsip_parse_hdr_func*) &parse_hdr_supported); 
    275     pjsip_register_hdr_parser( "To", "t", (pjsip_parse_hdr_func*) &parse_hdr_to); 
    276     pjsip_register_hdr_parser( "Unsupported", NULL, (pjsip_parse_hdr_func*) &parse_hdr_unsupported); 
    277     pjsip_register_hdr_parser( "Via", NULL, (pjsip_parse_hdr_func*) &parse_hdr_via); 
     238    status = pj_cis_init(&cis_buf, &pjsip_ARRAY_ELEMENTS); 
     239    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     240    pj_cis_add_str( &pjsip_ARRAY_ELEMENTS, ",\r\n"); 
     241 
     242    status = pj_cis_dup(&pjsip_TOKEN_SPEC, &pjsip_ALNUM_SPEC); 
     243    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     244    pj_cis_add_str( &pjsip_TOKEN_SPEC, TOKEN); 
     245 
     246    status = pj_cis_dup(&pjsip_HOST_SPEC, &pjsip_ALNUM_SPEC); 
     247    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     248    pj_cis_add_str( &pjsip_HOST_SPEC, HOST); 
     249 
     250    status = pj_cis_dup(&pjsip_HEX_SPEC, &pjsip_DIGIT_SPEC); 
     251    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     252    pj_cis_add_str( &pjsip_HEX_SPEC, HEX_DIGIT); 
     253 
     254    status = pj_cis_dup(&pjsip_PARAM_CHAR_SPEC, &pjsip_ALNUM_SPEC); 
     255    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     256    pj_cis_add_str(&pjsip_PARAM_CHAR_SPEC, PARAM_CHAR); 
     257 
     258    status = pj_cis_dup(&pjsip_USER_SPEC, &pjsip_ALNUM_SPEC); 
     259    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     260    pj_cis_add_str( &pjsip_USER_SPEC, MARK ESCAPED USER ); 
     261 
     262    status = pj_cis_dup(&pjsip_PASSWD_SPEC, &pjsip_ALNUM_SPEC); 
     263    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     264    pj_cis_add_str( &pjsip_PASSWD_SPEC, MARK ESCAPED PASS); 
     265 
     266    status = pj_cis_init(&cis_buf, &pjsip_PROBE_USER_HOST_SPEC); 
     267    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     268    pj_cis_add_str( &pjsip_PROBE_USER_HOST_SPEC, "@ \n>"); 
     269    pj_cis_invert( &pjsip_PROBE_USER_HOST_SPEC ); 
     270 
     271    status = pj_cis_init(&cis_buf, &pjsip_DISPLAY_SCAN_SPEC); 
     272    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     273    pj_cis_add_str( &pjsip_DISPLAY_SCAN_SPEC, ":\r\n<"); 
     274 
     275    status = pjsip_register_hdr_parser( "Accept", NULL, &parse_hdr_accept); 
     276    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     277 
     278    status = pjsip_register_hdr_parser( "Allow", NULL, &parse_hdr_allow); 
     279    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     280 
     281    status = pjsip_register_hdr_parser( "Call-ID", NULL, &parse_hdr_call_id); 
     282    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     283 
     284    status = pjsip_register_hdr_parser( "Contact", "m", &parse_hdr_contact); 
     285    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     286 
     287    status = pjsip_register_hdr_parser( "Content-Length", NULL,  
     288                                        &parse_hdr_content_len); 
     289    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     290 
     291    status = pjsip_register_hdr_parser( "Content-Type", NULL,  
     292                                        &parse_hdr_content_type); 
     293    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     294 
     295    status = pjsip_register_hdr_parser( "CSeq", NULL, &parse_hdr_cseq); 
     296    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     297 
     298    status = pjsip_register_hdr_parser( "Expires", NULL, &parse_hdr_expires); 
     299    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     300 
     301    status = pjsip_register_hdr_parser( "From", "f", &parse_hdr_from); 
     302    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     303 
     304    status = pjsip_register_hdr_parser( "Max-Forwards", NULL,  
     305                                        &parse_hdr_max_forwards); 
     306    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     307 
     308    status = pjsip_register_hdr_parser( "Min-Expires", NULL,  
     309                                        &parse_hdr_min_expires); 
     310    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     311 
     312    status = pjsip_register_hdr_parser( "Record-Route", NULL, &parse_hdr_rr); 
     313    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     314 
     315    status = pjsip_register_hdr_parser( "Route", NULL, &parse_hdr_route); 
     316    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     317 
     318    status = pjsip_register_hdr_parser( "Require", NULL, &parse_hdr_require); 
     319    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     320 
     321    status = pjsip_register_hdr_parser( "Retry-After", NULL,  
     322                                        &parse_hdr_retry_after); 
     323    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     324 
     325    status = pjsip_register_hdr_parser( "Supported", "k",  
     326                                        &parse_hdr_supported); 
     327    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     328 
     329    status = pjsip_register_hdr_parser( "To", "t", &parse_hdr_to); 
     330    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     331 
     332    status = pjsip_register_hdr_parser( "Unsupported", NULL,  
     333                                        &parse_hdr_unsupported); 
     334    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
     335 
     336    status = pjsip_register_hdr_parser( "Via", NULL, &parse_hdr_via); 
     337    PJ_ASSERT_RETURN(status == PJ_SUCCESS, status); 
    278338 
    279339    /* Register auth parser. */ 
    280     pjsip_auth_init_parser(); 
    281  
    282 } 
    283  
    284 static void init_sip_parser() 
     340    status = pjsip_auth_init_parser(); 
     341 
     342    return status; 
     343} 
     344 
     345static void init_sip_parser(void) 
    285346{ 
    286347    if (!parser_is_initialized) { 
     
    318379 
    319380    /* Equal length and equal hash. compare the strings. */ 
    320     return strcmp(r1->hname, name); 
     381    return pj_native_strcmp(r1->hname, name); 
    321382} 
    322383 
    323384/* Register one handler for one header name. */ 
    324 static int int_register_parser( const char *name, pjsip_parse_hdr_func *fptr ) 
     385static pj_status_t int_register_parser( const char *name,  
     386                                        pjsip_parse_hdr_func *fptr ) 
    325387{ 
    326388    unsigned    pos; 
     
    329391 
    330392    if (handler_count >= PJ_ARRAY_SIZE(handler)) { 
    331         return -1; 
     393        return PJ_ETOOMANY; 
    332394    } 
    333395 
     
    336398    rec.hname_len = strlen(name); 
    337399    if (rec.hname_len >= sizeof(rec.hname)) { 
    338         return -1; 
     400        return PJ_ENAMETOOLONG; 
    339401    } 
    340402    /* Name is copied in lowercase. */ 
    341403    for (i=0; i<rec.hname_len; ++i) { 
    342         rec.hname[i] = (char)tolower(name[i]); 
     404        rec.hname[i] = (char)pj_tolower(name[i]); 
    343405    } 
    344406    rec.hname[i] = '\0'; 
     
    349411    for (pos=0; pos < handler_count; ++pos) { 
    350412        int d; 
    351         d = compare_handler(&handler[pos], rec.hname, rec.hname_len, rec.hname_hash); 
     413        d = compare_handler(&handler[pos], rec.hname, rec.hname_len,  
     414                            rec.hname_hash); 
    352415        if (d == 0) { 
    353416            pj_assert(0); 
    354             return -1; 
     417            return PJ_EEXISTS; 
    355418        } 
    356419        if (d > 0) { 
     
    361424    /* Shift handlers. */ 
    362425    if (pos != handler_count) { 
    363         pj_memmove( &handler[pos+1], &handler[pos], (handler_count-pos)*sizeof(handler_rec)); 
     426        pj_memmove( &handler[pos+1], &handler[pos],  
     427                    (handler_count-pos)*sizeof(handler_rec)); 
    364428    } 
    365429    /* Add new handler. */ 
     
    367431    ++handler_count; 
    368432 
    369     return 0; 
     433    return PJ_SUCCESS; 
    370434} 
    371435 
     
    377441                                               pjsip_parse_hdr_func *fptr) 
    378442{ 
    379     if (int_register_parser(hname, fptr)) { 
    380         return -1; 
    381     } 
    382     if (hshortname && int_register_parser(hshortname, fptr)) { 
    383         return -1; 
    384     } 
    385     return 0; 
     443    pj_status_t status; 
     444 
     445    status = int_register_parser(hname, fptr); 
     446    if (status != PJ_SUCCESS) { 
     447        return status; 
     448    } 
     449    if (hshortname) { 
     450        status = int_register_parser(hshortname, fptr); 
     451        if (status != PJ_SUCCESS)  
     452            return status; 
     453    } 
     454    return PJ_SUCCESS; 
    386455} 
    387456 
     
    393462    pj_uint32_t  hash; 
    394463    int          comp; 
    395     unsigned     i, n; 
     464    unsigned     n; 
     465 
     466    if (hname->slen >= PJSIP_MAX_HNAME_LEN) { 
     467        pj_assert(!"Header name is too long!"); 
     468        return NULL; 
     469    } 
    396470 
    397471    /* Calculate hash value while converting the header to lowercase.  
    398472     * Don't assume that 'hname' is NULL terminated. 
    399473     */ 
    400     hash = 0; 
    401     for (i=0; i<(unsigned)hname->slen; ++i) { 
    402         hname_copy[i] = (char)tolower(hname->ptr[i]); 
    403         hash = hash * PJ_HASH_MULTIPLIER + hname_copy[i]; 
    404     } 
    405     hname_copy[i] = '\0'; 
     474    hash = pj_hash_calc_tolower(0, hname_copy, hname); 
     475    hname_copy[hname->slen] = '\0'; 
    406476 
    407477    /* Binary search for the handler. */ 
     
    429499 
    430500/* Public function to parse SIP message. */ 
    431 PJ_DEF(pjsip_msg*) pjsip_parse_msg( pj_pool_t *pool, char *buf, pj_size_t size, 
     501PJ_DEF(pjsip_msg*) pjsip_parse_msg( pj_pool_t *pool,  
     502                                    char *buf, pj_size_t size, 
    432503                                    pjsip_parser_err_report *err_list) 
    433504{ 
    434505    pjsip_msg *msg = NULL; 
    435506    pj_scanner scanner; 
     507    pjsip_parse_ctx context; 
    436508    PJ_USE_EXCEPTION; 
    437509 
    438510    init_sip_parser(); 
    439511 
    440     pj_scan_init(&scanner, buf, size, PJ_SCAN_AUTOSKIP_WS_HEADER, &on_syntax_error); 
     512    pj_scan_init(&scanner, buf, size, PJ_SCAN_AUTOSKIP_WS_HEADER,  
     513                 &on_syntax_error); 
     514 
     515    context.scanner = &scanner; 
     516    context.pool = pool; 
     517    context.rdata = NULL; 
    441518 
    442519    PJ_TRY { 
    443         msg = int_parse_msg(&scanner, pool, err_list); 
     520        msg = int_parse_msg(&context, err_list); 
    444521    }  
    445522    PJ_DEFAULT { 
     
    450527    pj_scan_fini(&scanner); 
    451528    return msg; 
     529} 
     530 
     531/* Public function to parse as rdata.*/ 
     532PJ_DEF(pjsip_msg *) pjsip_parse_rdata( char *buf, pj_size_t size, 
     533                                       pjsip_rx_data *rdata ) 
     534{ 
     535    pj_scanner scanner; 
     536    pjsip_parse_ctx context; 
     537    PJ_USE_EXCEPTION; 
     538 
     539    init_sip_parser(); 
     540 
     541    pj_scan_init(&scanner, buf, size, PJ_SCAN_AUTOSKIP_WS_HEADER,  
     542                 &on_syntax_error); 
     543 
     544    context.scanner = &scanner; 
     545    context.pool = rdata->pool; 
     546    context.rdata = rdata; 
     547 
     548    PJ_TRY { 
     549        rdata->msg = int_parse_msg(&context, &rdata->parse_err); 
     550    }  
     551    PJ_DEFAULT { 
     552        rdata->msg = NULL; 
     553    } 
     554    PJ_END 
     555 
     556    pj_scan_fini(&scanner); 
     557    return rdata->msg; 
    452558} 
    453559 
     
    467573    /* For datagram, the whole datagram IS the message. */ 
    468574    if (is_datagram) { 
    469         return PJ_TRUE; 
     575        return PJ_SUCCESS; 
    470576    } 
    471577 
    472578 
    473579    /* Find the end of header area by finding an empty line. */ 
    474     if ((pos = strstr(buf, "\n\r\n")) == NULL) { 
    475         return PJ_FALSE; 
     580    if ((pos = pj_native_strstr(buf, "\n\r\n")) == NULL) { 
     581        return PJSIP_EPARTIALMSG; 
    476582    } 
    477583 
     
    480586 
    481587    /* Find "Content-Length" header the hard way. */ 
    482     line = strchr(buf, '\n'); 
     588    line = pj_native_strchr(buf, '\n'); 
    483589    while (line && line < hdr_end-14) { 
    484590        ++line; 
    485         if ( ((*line=='C' || *line=='c') && strncasecmp(line, "Content-Length", 14) == 0) || 
    486              ((*line=='l' || *line=='L') && (*(line+1)==' ' || *(line+1)=='\t' || *(line+1)==':'))) 
     591        if ( ((*line=='C' || *line=='c') &&  
     592              pj_native_strncasecmp(line, "Content-Length", 14) == 0) || 
     593             ((*line=='l' || *line=='L') &&  
     594              (*(line+1)==' ' || *(line+1)=='\t' || *(line+1)==':'))) 
    487595        { 
    488596            /* Try to parse the header. */ 
     
    510618 
    511619                /* Get number */ 
    512                 pj_scan_get(&scanner, pjsip_DIGIT_SPEC, &str_clen); 
     620                pj_scan_get(&scanner, &pjsip_DIGIT_SPEC, &str_clen); 
    513621 
    514622                /* Get newline. */ 
     
    528636 
    529637        /* Go to next line. */ 
    530         line = strchr(line, '\n'); 
     638        line = pj_native_strchr(line, '\n'); 
    531639    } 
    532640 
    533641    /* Found Content-Length? */ 
    534642    if (content_length == -1) { 
    535         PJ_LOG(4, ("sipparser", "pjsip_find_msg: incoming TCP packet has missing " 
    536                              "Content-Length header, treated as incomplete.")); 
    537         return PJ_FALSE; 
     643        return PJSIP_EMISSINGHDR; 
    538644    } 
    539645 
    540646    /* Enough packet received? */ 
    541647    *msg_size = (body_start - buf) + content_length; 
    542     return (*msg_size) <= size; 
     648    return (*msg_size) <= size ? PJ_SUCCESS : PJSIP_EPARTIALMSG; 
    543649#else 
    544     PJ_UNUSED_ARG(buf) 
    545     PJ_UNUSED_ARG(is_datagram) 
     650    PJ_UNUSED_ARG(buf); 
     651    PJ_UNUSED_ARG(is_datagram); 
    546652    *msg_size = size; 
    547     return 1; 
     653    return PJ_SUCCESS; 
    548654#endif 
    549655} 
     
    558664    pjsip_uri *uri = NULL; 
    559665 
    560     if (!parser_is_initialized) { 
    561         init_parser(); 
    562         parser_is_initialized = 1; 
    563     } 
     666    init_sip_parser(); 
    564667 
    565668    pj_scan_init(&scanner, buf, size, 0, &on_syntax_error); 
     
    572675 
    573676    /* Must have exhausted all inputs. */ 
    574     if (pj_scan_is_eof(&scanner) || *scanner.current=='\r' || *scanner.current=='\n') { 
     677    if (pj_scan_is_eof(&scanner) || *scanner.curptr=='\r' ||  
     678                       *scanner.curptr=='\n')  
     679    { 
    575680        /* Success. */ 
    576681        pj_scan_fini(&scanner); 
     
    587692 * actual body is laid. 
    588693 */ 
    589 static int generic_print_body (pjsip_msg_body *msg_body, char *buf, pj_size_t size) 
     694static int generic_print_body (pjsip_msg_body *msg_body,  
     695                               char *buf, pj_size_t size) 
    590696{ 
    591697    pjsip_msg_body *body = msg_body; 
     
    598704 
    599705/* Internal function to parse SIP message */ 
    600 static pjsip_msg *int_parse_msg( pj_scanner *scanner, pj_pool_t *pool,  
     706static pjsip_msg *int_parse_msg( pjsip_parse_ctx *ctx, 
    601707                                 pjsip_parser_err_report *err_list) 
    602708{ 
     
    605711    pjsip_msg *msg; 
    606712    pjsip_ctype_hdr *ctype_hdr = NULL; 
     713    pj_scanner *scanner = ctx->scanner; 
     714    pj_pool_t *pool = ctx->pool; 
    607715 
    608716    /* Skip leading newlines. */ 
    609     ch = *scanner->current; 
     717    ch = *scanner->curptr; 
    610718    while (ch=='\r' || ch=='\n') { 
    611719        pj_scan_get_char(scanner); 
    612         ch = *scanner->current; 
     720        ch = *scanner->curptr; 
    613721    } 
    614722 
     
    631739 
    632740        /* Get hname. */ 
    633         pj_scan_get( scanner, pjsip_TOKEN_SPEC, &hname); 
     741        pj_scan_get( scanner, &pjsip_TOKEN_SPEC, &hname); 
    634742        ch = pj_scan_get_char( scanner ); 
    635743        if (ch != ':') { 
     
    646754             */ 
    647755            if (handler) { 
    648                 hdr = (*handler)(scanner, pool); 
     756                hdr = (*handler)(ctx); 
    649757            } else { 
    650                 pjsip_generic_string_hdr *ghdr = parse_hdr_generic_string(scanner, pool); 
    651                 ghdr->type = PJSIP_H_OTHER; 
    652                 ghdr->name = ghdr->sname = hname; 
    653                 hdr = (pjsip_hdr*)ghdr; 
     758                hdr = parse_hdr_generic_string(ctx); 
     759                hdr->type = PJSIP_H_OTHER; 
     760                hdr->name = hdr->sname = hname; 
    654761            } 
    655762 
     
    669776            hdr = NULL; 
    670777 
    671             PJ_LOG(4,("sipparser", "Syntax error in line %d col %d (hname=%.*s)", 
    672                       scanner->line, scanner->col, hname.slen, hname.ptr)); 
     778            //PJ_LOG(4,("sipparser",  
     779            //          "Syntax error in line %d col %d (hname=%.*s)", 
     780            //        scanner->line, scanner->col, hname.slen, hname.ptr)); 
    673781 
    674782            if (err_list) { 
     
    685793 
    686794            if (!pj_scan_is_eof(scanner)) { 
    687                 pj_scan_get_until(scanner, pjsip_NEWLINE_OR_EOF_SPEC, &token); 
     795                pj_scan_get_until(scanner, &pjsip_NEWLINE_OR_EOF_SPEC, &token); 
    688796                parse_hdr_end(scanner); 
    689797            } 
     
    703811        /* Parse until EOF or an empty line is found. */ 
    704812    } while (!pj_scan_is_eof(scanner) &&  
    705               *scanner->current != '\r' && *scanner->current != '\n'); 
     813              *scanner->curptr != '\r' && *scanner->curptr != '\n'); 
    706814 
    707815    /* If empty line is found, eat it. */ 
    708816    if (!pj_scan_is_eof(scanner)) { 
    709         if (*scanner->current=='\r' || *scanner->current=='\n') { 
     817        if (*scanner->curptr=='\r' || *scanner->curptr=='\n') { 
    710818            pj_scan_get_newline(scanner); 
    711819        } 
    712820    } 
    713821 
    714     /* If we have Content-Type header, treat the rest of the message as body. */ 
     822    /* If we have Content-Type header, treat the rest of the message as body.*/ 
    715823    if (ctype_hdr) { 
    716824        pjsip_msg_body *body = pj_pool_alloc(pool, sizeof(pjsip_msg_body)); 
    717         pj_strdup (pool, &body->content_type.type, &ctype_hdr->media.type); 
    718         pj_strdup (pool, &body->content_type.subtype, &ctype_hdr->media.subtype); 
    719         pj_strdup (pool, &body->content_type.param, &ctype_hdr->media.param); 
    720         body->data = scanner->current; 
    721         body->len = scanner->end - scanner->current; 
     825        pj_strdup(pool, &body->content_type.type, &ctype_hdr->media.type); 
     826        pj_strdup(pool, &body->content_type.subtype, &ctype_hdr->media.subtype); 
     827        pj_strdup(pool, &body->content_type.param, &ctype_hdr->media.param); 
     828        body->data = scanner->curptr; 
     829        body->len = scanner->end - scanner->curptr; 
    722830        body->print_body = &generic_print_body; 
    723831 
     
    734842{ 
    735843    /* pname */ 
    736     pj_scan_get(scanner, pjsip_PARAM_CHAR_SPEC, pname); 
     844    pj_scan_get(scanner, &pjsip_PARAM_CHAR_SPEC, pname); 
    737845 
    738846    /* pvalue, if any */ 
    739     if (*scanner->current == '=') { 
     847    if (*scanner->curptr == '=') { 
    740848        pj_scan_get_char(scanner); 
    741849        /* pvalue can be a quoted string. */ 
    742         if (*scanner->current == '"') { 
     850        if (*scanner->curptr == '"') { 
    743851            pj_scan_get_quote( scanner, '"', '"', pvalue); 
    744852            if (option & PJSIP_PARSE_REMOVE_QUOTE) { 
     
    747855            } 
    748856        } else { 
    749             pj_scan_get(scanner, pjsip_PARAM_CHAR_SPEC, pvalue); 
     857            pj_scan_get(scanner, &pjsip_PARAM_CHAR_SPEC, pvalue); 
    750858        } 
    751859    } else { 
     
    770878                                     pj_str_t *host, int *p_port) 
    771879{ 
    772     pj_scan_get( scanner, pjsip_HOST_SPEC, host); 
    773     if (*scanner->current == ':') { 
     880    pj_scan_get( scanner, &pjsip_HOST_SPEC, host); 
     881    if (*scanner->curptr == ':') { 
    774882        pj_str_t port; 
    775883        pj_scan_get_char(scanner); 
    776         pj_scan_get(scanner, pjsip_DIGIT_SPEC, &port); 
     884        pj_scan_get(scanner, &pjsip_DIGIT_SPEC, &port); 
    777885        *p_port = pj_strtoul(&port); 
    778886    } else { 
     
    790898     * must be a username. 
    791899     */ 
    792     if (pj_scan_peek( scanner, pjsip_PROBE_USER_HOST_SPEC, &dummy) == '@') 
     900    if (pj_scan_peek( scanner, &pjsip_PROBE_USER_HOST_SPEC, &dummy) == '@') 
    793901        is_user = 1; 
    794902    else 
     
    802910                                 pj_str_t *user, pj_str_t *pass) 
    803911{ 
    804     pj_scan_get( scanner, pjsip_USER_SPEC, user); 
    805     if ( *scanner->current == ':') { 
     912    pj_scan_get( scanner, &pjsip_USER_SPEC, user); 
     913    if ( *scanner->curptr == ':') { 
    806914        pj_scan_get_char( scanner ); 
    807         pj_scan_get( scanner, pjsip_PASSWD_SPEC, pass); 
     915        pj_scan_get( scanner, &pjsip_PASSWD_SPEC, pass); 
    808916    } else { 
    809917        pass->ptr = NULL; 
     
    816924 
    817925/* Parse all types of URI. */ 
    818 static pjsip_uri *int_parse_uri_or_name_addr(pj_scanner *scanner, pj_pool_t *pool, 
    819                                                   unsigned option) 
     926static pjsip_uri *int_parse_uri_or_name_addr( pj_scanner *scanner, pj_pool_t *pool, 
     927                                              unsigned opt) 
    820928{ 
    821929    pjsip_uri *uri; 
    822930    int is_name_addr = 0; 
    823931 
    824     if (*scanner->current=='"' || *scanner->current=='<') { 
     932    if (*scanner->curptr=='"' || *scanner->curptr=='<') { 
    825933        uri = (pjsip_uri*)int_parse_name_addr( scanner, pool ); 
    826934        is_name_addr = 1; 
     
    831939 
    832940        pj_scan_save_state( scanner, &backtrack); 
    833         pj_scan_get( scanner, pjsip_TOKEN_SPEC, &scheme); 
     941        pj_scan_get( scanner, &pjsip_TOKEN_SPEC, &scheme); 
    834942        colon = pj_scan_get_char( scanner ); 
    835943        pj_scan_restore_state( scanner, &backtrack); 
    836944 
    837         if (colon==':' && (parser_stricmp(scheme, pjsip_SIP_STR)==0 || parser_stricmp(scheme, pjsip_SIPS_STR)==0))  
     945        if (colon==':' &&  
     946            (parser_stricmp(scheme, pjsip_SIP_STR)==0 ||  
     947             parser_stricmp(scheme, pjsip_SIPS_STR)==0))  
    838948        { 
    839             uri = (pjsip_uri*)int_parse_sip_url( scanner, pool,  
    840                                         (option & PJSIP_PARSE_URI_IN_FROM_TO_HDR) == 0 ); 
     949            uri = (pjsip_uri*) 
     950                int_parse_sip_url( scanner, pool,  
     951                                   (opt & PJSIP_PARSE_URI_IN_FROM_TO_HDR)== 0); 
    841952 
    842953        } else if (colon==':' && parser_stricmp( scheme, pjsip_TEL_STR)==0) { 
     
    853964 
    854965    /* Should we return the URI object as name address? */ 
    855     if (option & PJSIP_PARSE_URI_AS_NAMEADDR) { 
     966    if (opt & PJSIP_PARSE_URI_AS_NAMEADDR) { 
    856967        if (is_name_addr == 0) { 
    857968            pjsip_name_addr *name_addr; 
     
    871982                                pj_bool_t parse_params) 
    872983{ 
    873     if (*scanner->current=='"' || *scanner->current=='<') { 
     984    if (*scanner->curptr=='"' || *scanner->curptr=='<') { 
    874985        return (pjsip_uri*)int_parse_name_addr( scanner, pool ); 
    875986    } else { 
     
    878989 
    879990        /* Get scheme. */ 
    880         colon = pj_scan_peek(scanner, pjsip_TOKEN_SPEC, &scheme); 
     991        colon = pj_scan_peek(scanner, &pjsip_TOKEN_SPEC, &scheme); 
    881992        if (colon != ':') { 
    882993            PJ_THROW(PJSIP_SYN_ERR_EXCEPTION); 
    883994        } 
    884995 
    885         if ((parser_stricmp(scheme, pjsip_SIP_STR)==0 || parser_stricmp(scheme, pjsip_SIPS_STR)==0))  
     996        if ((parser_stricmp(scheme, pjsip_SIP_STR)==0 ||  
     997            parser_stricmp(scheme, pjsip_SIPS_STR)==0))  
    886998        { 
    887             return (pjsip_uri*)int_parse_sip_url( scanner, pool, parse_params ); 
     999            return (pjsip_uri*)int_parse_sip_url( scanner, pool, parse_params); 
    8881000 
    8891001        } else if (parser_stricmp(scheme, pjsip_TEL_STR)==0) { 
     
    9091021    scanner->skip_ws = 0; 
    9101022 
    911     pj_scan_get(scanner, pjsip_TOKEN_SPEC, &scheme); 
     1023    pj_scan_get(scanner, &pjsip_TOKEN_SPEC, &scheme); 
    9121024    colon = pj_scan_get_char(scanner); 
    9131025    if (colon != ':') { 
     
    9381050 
    9391051    /* Get URL parameters. */ 
    940     while ( parse_params && *scanner->current == ';' ) { 
     1052    while ( parse_params && *scanner->curptr == ';' ) { 
    9411053        pj_str_t pname, pvalue; 
    9421054 
     
    9491061            url->method_param = pvalue; 
    9501062 
    951         } else if (!parser_stricmp(pname, pjsip_TRANSPORT_STR) && pvalue.slen) { 
     1063        } else if (!parser_stricmp(pname,pjsip_TRANSPORT_STR) && pvalue.slen) { 
    9521064            url->transport_param = pvalue; 
    9531065 
     
    9671079 
    9681080    /* Get header params. */ 
    969     if (parse_params && *scanner->current == '?') { 
    970         pj_scan_get_until(scanner, pjsip_NEWLINE_OR_EOF_SPEC, &url->header_param); 
     1081    if (parse_params && *scanner->curptr == '?') { 
     1082        pj_scan_get_until(scanner, &pjsip_NEWLINE_OR_EOF_SPEC,  
     1083                          &url->header_param); 
    9711084    } 
    9721085 
     
    9851098    name_addr = pjsip_name_addr_create(pool); 
    9861099 
    987     if (*scanner->current == '"') { 
     1100    if (*scanner->curptr == '"') { 
    9881101        pj_scan_get_quote( scanner, '"', '"', &name_addr->display); 
    9891102 
    990     } else if (*scanner->current != '<') { 
     1103    } else if (*scanner->curptr != '<') { 
    9911104        int next; 
    9921105        pj_str_t dummy; 
     
    9971110         * will be parser later. 
    9981111         */ 
    999         next = pj_scan_peek_until(scanner, pjsip_DISPLAY_SCAN_SPEC, &dummy); 
     1112        next = pj_scan_peek_until(scanner, &pjsip_DISPLAY_SCAN_SPEC, &dummy); 
    10001113        if (next == '<') { 
    10011114            /* Ok, this is what we're looking for, a display name. */ 
     
    10091122 
    10101123    /* Get the SIP-URL */ 
    1011     has_bracket = (*scanner->current == '<'); 
     1124    has_bracket = (*scanner->curptr == '<'); 
    10121125    if (has_bracket) 
    10131126        pj_scan_get_char(scanner); 
     
    10261139    pj_str_t token; 
    10271140 
    1028     pj_scan_get( scanner, pjsip_TOKEN_SPEC, &token); 
     1141    pj_scan_get( scanner, &pjsip_TOKEN_SPEC, &token); 
    10291142    pjsip_method_init_np( &req_line->method, &token); 
    10301143 
     
    10461159    pj_scan_advance_n( scanner, 7, 1); 
    10471160 
    1048     pj_scan_get( scanner, pjsip_DIGIT_SPEC, &token); 
     1161    pj_scan_get( scanner, &pjsip_DIGIT_SPEC, &token); 
    10491162    status_line->code = pj_strtoul(&token); 
    1050     pj_scan_get_until( scanner, pjsip_NEWLINE_OR_EOF_SPEC, &status_line->reason); 
     1163    pj_scan_get_until( scanner, &pjsip_NEWLINE_OR_EOF_SPEC,  
     1164                       &status_line->reason); 
    10511165    pj_scan_get_newline( scanner ); 
    10521166} 
     
    10571171    if (pj_scan_is_eof(scanner)) { 
    10581172        ;   /* Do nothing. */ 
    1059     } else if (*scanner->current == '&') { 
     1173    } else if (*scanner->curptr == '&') { 
    10601174        pj_scan_get_char(scanner); 
    10611175    } else { 
     
    10741188                                     pj_scanner *scanner) 
    10751189{ 
    1076     pj_scan_get_until( scanner, pjsip_ARRAY_ELEMENTS, &hdr->values[0]); 
     1190    pj_scan_get_until( scanner, &pjsip_ARRAY_ELEMENTS, &hdr->values[0]); 
    10771191    hdr->count++; 
    10781192 
    1079     while (*scanner->current == ',') { 
     1193    while (*scanner->curptr == ',') { 
    10801194        pj_scan_get_char(scanner); 
    1081         pj_scan_get_until( scanner, pjsip_ARRAY_ELEMENTS, &hdr->values[hdr->count]); 
     1195        pj_scan_get_until( scanner, &pjsip_ARRAY_ELEMENTS,  
     1196                           &hdr->values[hdr->count]); 
    10821197        hdr->count++; 
    10831198    } 
     
    10891204                                      pj_scanner *scanner ) 
    10901205{ 
    1091     pj_scan_get_until( scanner, pjsip_NEWLINE_OR_EOF_SPEC, &hdr->hvalue); 
     1206    pj_scan_get_until( scanner, &pjsip_NEWLINE_OR_EOF_SPEC, &hdr->hvalue); 
    10921207    parse_hdr_end(scanner); 
    10931208} 
     
    10981213{ 
    10991214    pj_str_t tmp; 
    1100     pj_scan_get_until( scanner, pjsip_NEWLINE_OR_EOF_SPEC, &tmp); 
     1215    pj_scan_get_until( scanner, &pjsip_NEWLINE_OR_EOF_SPEC, &tmp); 
    11011216    hdr->ivalue = pj_strtoul(&tmp); 
    11021217    parse_hdr_end(scanner); 
     
    11051220 
    11061221/* Parse Accept header. */ 
    1107 static pjsip_accept_hdr* parse_hdr_accept( pj_scanner *scanner,  
    1108                                             pj_pool_t *pool) 
    1109 { 
    1110     pjsip_accept_hdr *accept = pjsip_accept_hdr_create(pool); 
    1111     parse_generic_array_hdr(accept, scanner); 
    1112     return accept; 
     1222static pjsip_hdr* parse_hdr_accept(pjsip_parse_ctx *ctx) 
     1223{ 
     1224    pjsip_accept_hdr *accept = pjsip_accept_hdr_create(ctx->pool); 
     1225    parse_generic_array_hdr(accept, ctx->scanner); 
     1226    return (pjsip_hdr*)accept; 
    11131227} 
    11141228 
    11151229/* Parse Allow header. */ 
    1116 static pjsip_allow_hdr*   parse_hdr_allow( pj_scanner *scanner,  
    1117                                            pj_pool_t *pool) 
    1118 { 
    1119     pjsip_allow_hdr *allow = pjsip_allow_hdr_create(pool); 
    1120     parse_generic_array_hdr(allow, scanner); 
    1121     return allow; 
     1230static pjsip_hdr* parse_hdr_allow(pjsip_parse_ctx *ctx) 
     1231{ 
     1232    pjsip_allow_hdr *allow = pjsip_allow_hdr_create(ctx->pool); 
     1233    parse_generic_array_hdr(allow, ctx->scanner); 
     1234    return (pjsip_hdr*)allow; 
    11221235} 
    11231236 
    11241237/* Parse Call-ID header. */ 
    1125 static pjsip_cid_hdr* parse_hdr_call_id( pj_scanner *scanner,  
    1126                                           pj_pool_t *pool) 
    1127 { 
    1128     pjsip_cid_hdr *hdr = pjsip_cid_hdr_create(pool); 
    1129     pj_scan_get_until( scanner, pjsip_NEWLINE_OR_EOF_SPEC, &hdr->id); 
    1130     parse_hdr_end(scanner); 
    1131     return hdr; 
     1238static pjsip_hdr* parse_hdr_call_id(pjsip_parse_ctx *ctx) 
     1239{ 
     1240    pjsip_cid_hdr *hdr = pjsip_cid_hdr_create(ctx->pool); 
     1241    pj_scan_get_until( ctx->scanner, &pjsip_NEWLINE_OR_EOF_SPEC, &hdr->id); 
     1242    parse_hdr_end(ctx->scanner); 
     1243 
     1244    if (ctx->rdata) 
     1245        ctx->rdata->call_id = hdr->id; 
     1246 
     1247    return (pjsip_hdr*)hdr; 
    11321248} 
    11331249 
     
    11371253                                     pj_pool_t *pool) 
    11381254{ 
    1139     while ( *scanner->current == ';' ) { 
     1255    while ( *scanner->curptr == ';' ) { 
    11401256        pj_str_t pname, pvalue; 
    11411257 
     
    11601276 
    11611277/* Parse Contact header. */ 
    1162 PJ_DEF(pjsip_contact_hdr*) parse_hdr_contact( pj_scanner *scanner,  
    1163                                               pj_pool_t *pool) 
     1278static pjsip_hdr* parse_hdr_contact( pjsip_parse_ctx *ctx ) 
    11641279{ 
    11651280    pjsip_contact_hdr *first = NULL; 
     1281    pj_scanner *scanner = ctx->scanner; 
    11661282     
    11671283    do { 
    1168         pjsip_contact_hdr *hdr = pjsip_contact_hdr_create(pool); 
     1284        pjsip_contact_hdr *hdr = pjsip_contact_hdr_create(ctx->pool); 
    11691285        if (first == NULL) 
    11701286            first = hdr; 
     
    11721288            pj_list_insert_before(first, hdr); 
    11731289 
    1174         if (*scanner->current == '*') { 
     1290        if (*scanner->curptr == '*') { 
    11751291            pj_scan_get_char(scanner); 
    11761292            hdr->star = 1; 
     
    11781294        } else { 
    11791295            hdr->star = 0; 
    1180             hdr->uri = int_parse_uri_or_name_addr(scanner, pool, PJSIP_PARSE_URI_AS_NAMEADDR); 
    1181  
    1182             int_parse_contact_param(hdr, scanner, pool); 
    1183         } 
    1184  
    1185         if (*scanner->current != ',') 
     1296            hdr->uri = int_parse_uri_or_name_addr(scanner, ctx->pool,  
     1297                                                  PJSIP_PARSE_URI_AS_NAMEADDR); 
     1298 
     1299            int_parse_contact_param(hdr, scanner, ctx->pool); 
     1300        } 
     1301 
     1302        if (*scanner->curptr != ',') 
    11861303            break; 
    11871304 
     
    11911308 
    11921309    parse_hdr_end(scanner); 
    1193     return first; 
     1310 
     1311    return (pjsip_hdr*)first; 
    11941312} 
    11951313 
    11961314/* Parse Content-Length header. */ 
    1197 PJ_DEF(pjsip_clen_hdr*) parse_hdr_content_length( pj_scanner *scanner,  
    1198                                                   pj_pool_t *pool) 
     1315static pjsip_hdr* parse_hdr_content_len( pjsip_parse_ctx *ctx ) 
    11991316{ 
    12001317    pj_str_t digit; 
    12011318    pjsip_clen_hdr *hdr; 
    12021319 
    1203     hdr = pjsip_clen_hdr_create(pool); 
    1204     pj_scan_get(scanner, pjsip_DIGIT_SPEC, &digit); 
     1320    hdr = pjsip_clen_hdr_create(ctx->pool); 
     1321    pj_scan_get(ctx->scanner, &pjsip_DIGIT_SPEC, &digit); 
    12051322    hdr->len = pj_strtoul(&digit); 
    1206     parse_hdr_end(scanner); 
    1207     return hdr; 
     1323    parse_hdr_end(ctx->scanner); 
     1324 
     1325    if (ctx->rdata) 
     1326        ctx->rdata->clen = hdr; 
     1327 
     1328    return (pjsip_hdr*)hdr; 
    12081329} 
    12091330 
    12101331/* Parse Content-Type header. */ 
    1211 PJ_DEF(pjsip_ctype_hdr*) parse_hdr_content_type( pj_scanner *scanner,  
    1212                                                  pj_pool_t *pool) 
     1332static pjsip_hdr* parse_hdr_content_type( pjsip_parse_ctx *ctx ) 
    12131333{ 
    12141334    pjsip_ctype_hdr *hdr; 
    1215  
    1216     hdr = pjsip_ctype_hdr_create(pool); 
     1335    pj_scanner *scanner = ctx->scanner; 
     1336 
     1337    hdr = pjsip_ctype_hdr_create(ctx->pool); 
    12171338     
    12181339    /* Parse media type and subtype. */ 
    1219     pj_scan_get(scanner, pjsip_TOKEN_SPEC, &hdr->media.type); 
     1340    pj_scan_get(scanner, &pjsip_TOKEN_SPEC, &hdr->media.type); 
    12201341    pj_scan_get_char(scanner); 
    1221     pj_scan_get(scanner, pjsip_TOKEN_SPEC, &hdr->media.subtype); 
     1342    pj_scan_get(scanner, &pjsip_TOKEN_SPEC, &hdr->media.subtype); 
    12221343 
    12231344    /* Parse media parameters */ 
    1224     while (*scanner->current == ';') { 
     1345    while (*scanner->curptr == ';') { 
    12251346        pj_str_t pname, pvalue; 
    12261347        int_parse_param(scanner, &pname, &pvalue); 
    1227         concat_param(&hdr->media.param, pool, &pname, &pvalue); 
    1228     } 
    1229  
    1230     parse_hdr_end(scanner); 
    1231     return hdr; 
     1348        concat_param(&hdr->media.param, ctx->pool, &pname, &pvalue); 
     1349    } 
     1350 
     1351    parse_hdr_end(ctx->scanner); 
     1352 
     1353    if (ctx->rdata) 
     1354        ctx->rdata->ctype = hdr; 
     1355 
     1356    return (pjsip_hdr*)hdr; 
    12321357} 
    12331358 
    12341359/* Parse CSeq header. */ 
    1235 PJ_DEF(pjsip_cseq_hdr*) parse_hdr_cseq( pj_scanner *scanner,  
    1236                                         pj_pool_t *pool) 
     1360static pjsip_hdr* parse_hdr_cseq( pjsip_parse_ctx *ctx ) 
    12371361{ 
    12381362    pj_str_t cseq, method; 
    12391363    pjsip_cseq_hdr *hdr; 
    12401364 
    1241     hdr = pjsip_cseq_hdr_create(pool); 
    1242     pj_scan_get( scanner, pjsip_DIGIT_SPEC, &cseq); 
     1365    hdr = pjsip_cseq_hdr_create(ctx->pool); 
     1366    pj_scan_get( ctx->scanner, &pjsip_DIGIT_SPEC, &cseq); 
    12431367    hdr->cseq = pj_strtoul(&cseq); 
    12441368 
    1245     pj_scan_get( scanner, pjsip_TOKEN_SPEC, &method); 
     1369    pj_scan_get( ctx->scanner, &pjsip_TOKEN_SPEC, &method); 
    12461370    pjsip_method_init_np(&hdr->method, &method); 
    12471371 
    1248     parse_hdr_end( scanner ); 
    1249     return hdr; 
     1372    parse_hdr_end( ctx->scanner ); 
     1373 
     1374    if (ctx->rdata) 
     1375        ctx->rdata->cseq = hdr; 
     1376 
     1377    return (pjsip_hdr*)hdr; 
    12501378} 
    12511379 
    12521380/* Parse Expires header. */ 
    1253 static pjsip_expires_hdr* parse_hdr_expires(pj_scanner *scanner,  
    1254                                             pj_pool_t *pool) 
    1255 { 
    1256     pjsip_expires_hdr *hdr = pjsip_expires_hdr_create(pool); 
    1257     parse_generic_int_hdr(hdr, scanner); 
    1258     return hdr; 
     1381static pjsip_hdr* parse_hdr_expires(pjsip_parse_ctx *ctx) 
     1382{ 
     1383    pjsip_expires_hdr *hdr = pjsip_expires_hdr_create(ctx->pool); 
     1384    parse_generic_int_hdr(hdr, ctx->scanner); 
     1385    return (pjsip_hdr*)hdr; 
    12591386} 
    12601387 
     
    12681395                                          PJSIP_PARSE_URI_IN_FROM_TO_HDR); 
    12691396 
    1270     while ( *scanner->current == ';' ) { 
     1397    while ( *scanner->curptr == ';' ) { 
    12711398        pj_str_t pname, pvalue; 
    12721399 
     
    12851412 
    12861413/* Parse From: header. */ 
    1287 PJ_DEF(pjsip_from_hdr*) parse_hdr_from( pj_scanner *scanner,  
    1288                                         pj_pool_t *pool) 
    1289 { 
    1290     pjsip_from_hdr *hdr = pjsip_from_hdr_create(pool); 
    1291     parse_hdr_fromto(scanner, pool, hdr); 
    1292     return hdr; 
     1414static pjsip_hdr* parse_hdr_from( pjsip_parse_ctx *ctx ) 
     1415{ 
     1416    pjsip_from_hdr *hdr = pjsip_from_hdr_create(ctx->pool); 
     1417    parse_hdr_fromto(ctx->scanner, ctx->pool, hdr); 
     1418    if (ctx->rdata) 
     1419        ctx->rdata->from = hdr; 
     1420 
     1421    return (pjsip_hdr*)hdr; 
    12931422} 
    12941423 
    12951424/* Parse Require: header. */ 
    1296 static pjsip_require_hdr* parse_hdr_require( pj_scanner *scanner,  
    1297                                              pj_pool_t *pool) 
    1298 { 
    1299     pjsip_require_hdr *hdr = pjsip_require_hdr_create(pool); 
    1300     parse_generic_array_hdr(hdr, scanner); 
    1301     return hdr; 
     1425static pjsip_hdr* parse_hdr_require( pjsip_parse_ctx *ctx ) 
     1426{ 
     1427    pjsip_require_hdr *hdr = pjsip_require_hdr_create(ctx->pool); 
     1428    parse_generic_array_hdr(hdr, ctx->scanner); 
     1429 
     1430    if (ctx->rdata && ctx->rdata->require == NULL) 
     1431        ctx->rdata->require = hdr; 
     1432 
     1433    return (pjsip_hdr*)hdr; 
    13021434} 
    13031435 
    13041436/* Parse Retry-After: header. */ 
    1305 static pjsip_retry_after_hdr* parse_hdr_retry_after(pj_scanner *scanner,  
    1306                                                     pj_pool_t *pool) 
     1437static pjsip_hdr* parse_hdr_retry_after(pjsip_parse_ctx *ctx) 
    13071438{ 
    13081439    pjsip_retry_after_hdr *hdr; 
    1309     hdr = pjsip_retry_after_hdr_create(pool); 
    1310     parse_generic_int_hdr(hdr, scanner); 
    1311     return hdr; 
     1440    hdr = pjsip_retry_after_hdr_create(ctx->pool); 
     1441    parse_generic_int_hdr(hdr, ctx->scanner); 
     1442    return (pjsip_hdr*)hdr; 
    13121443} 
    13131444 
    13141445/* Parse Supported: header. */ 
    1315 static pjsip_supported_hdr* parse_hdr_supported(pj_scanner *scanner,  
    1316                                                 pj_pool_t *pool) 
    1317 { 
    1318     pjsip_supported_hdr *hdr = pjsip_supported_hdr_create(pool); 
    1319     parse_generic_array_hdr(hdr, scanner); 
    1320     return hdr; 
     1446static pjsip_hdr* parse_hdr_supported(pjsip_parse_ctx *ctx) 
     1447{ 
     1448    pjsip_supported_hdr *hdr = pjsip_supported_hdr_create(ctx->pool); 
     1449    parse_generic_array_hdr(hdr, ctx->scanner); 
     1450    return (pjsip_hdr*)hdr; 
    13211451} 
    13221452 
    13231453 
    13241454/* Parse To: header. */ 
    1325 PJ_DEF(pjsip_to_hdr*) parse_hdr_to( pj_scanner *scanner,  
    1326                                     pj_pool_t *pool) 
    1327 { 
    1328     pjsip_to_hdr *hdr = pjsip_to_hdr_create(pool); 
    1329     parse_hdr_fromto(scanner, pool, hdr); 
    1330     return hdr; 
     1455static pjsip_hdr* parse_hdr_to( pjsip_parse_ctx *ctx ) 
     1456{ 
     1457    pjsip_to_hdr *hdr = pjsip_to_hdr_create(ctx->pool); 
     1458    parse_hdr_fromto(ctx->scanner, ctx->pool, hdr); 
     1459 
     1460    if (ctx->rdata) 
     1461        ctx->rdata->to = hdr; 
     1462 
     1463    return (pjsip_hdr*)hdr; 
    13311464} 
    13321465 
    13331466/* Parse Unsupported: header. */ 
    1334 static pjsip_unsupported_hdr* parse_hdr_unsupported(pj_scanner *scanner,  
    1335                                                     pj_pool_t *pool) 
    1336 { 
    1337     pjsip_unsupported_hdr *hdr = pjsip_unsupported_hdr_create(pool); 
    1338     parse_generic_array_hdr(hdr, scanner); 
    1339     return hdr; 
     1467static pjsip_hdr* parse_hdr_unsupported(pjsip_parse_ctx *ctx) 
     1468{ 
     1469    pjsip_unsupported_hdr *hdr = pjsip_unsupported_hdr_create(ctx->pool); 
     1470    parse_generic_array_hdr(hdr, ctx->scanner); 
     1471    return (pjsip_hdr*)hdr; 
    13401472} 
    13411473 
     
    13441476                                 pj_pool_t *pool) 
    13451477{ 
    1346     while ( *scanner->current == ';' ) { 
     1478    while ( *scanner->curptr == ';' ) { 
    13471479        pj_str_t pname, pvalue; 
    13481480 
     
    13741506 
    13751507/* Parse Max-Forwards header. */ 
    1376 static pjsip_max_forwards_hdr* parse_hdr_max_forwards( pj_scanner *scanner,  
    1377                                                        pj_pool_t *pool) 
     1508static pjsip_hdr* parse_hdr_max_forwards( pjsip_parse_ctx *ctx ) 
    13781509{ 
    13791510    pjsip_max_forwards_hdr *hdr; 
    1380     hdr = pjsip_max_forwards_hdr_create(pool); 
    1381     parse_generic_int_hdr(hdr, scanner); 
    1382     return hdr; 
     1511    hdr = pjsip_max_forwards_hdr_create(ctx->pool); 
     1512    parse_generic_int_hdr(hdr, ctx->scanner); 
     1513 
     1514    if (ctx->rdata) 
     1515        ctx->rdata->max_fwd = hdr; 
     1516 
     1517    return (pjsip_hdr*)hdr; 
    13831518} 
    13841519 
    13851520/* Parse Min-Expires header. */ 
    1386 static pjsip_min_expires_hdr*  parse_hdr_min_expires(pj_scanner *scanner,  
    1387                                                      pj_pool_t *pool) 
     1521static pjsip_hdr* parse_hdr_min_expires(pjsip_parse_ctx *ctx) 
    13881522{ 
    13891523    pjsip_min_expires_hdr *hdr; 
    1390     hdr = pjsip_min_expires_hdr_create(pool); 
    1391     parse_generic_int_hdr(hdr, scanner); 
    1392     return hdr; 
     1524    hdr = pjsip_min_expires_hdr_create(ctx->pool); 
     1525    parse_generic_int_hdr(hdr, ctx->scanner); 
     1526    return (pjsip_hdr*)hdr; 
    13931527} 
    13941528 
     
    14011535 
    14021536    pj_memcpy(&hdr->name_addr, temp, sizeof(*temp)); 
    1403     if (*scanner->current == ';') { 
    1404         pj_scan_get_until(scanner, pjsip_NEWLINE_OR_EOF_SPEC, &hdr->other_param); 
     1537    if (*scanner->curptr == ';') { 
     1538        pj_scan_get_until(scanner, &pjsip_NEWLINE_OR_EOF_SPEC,  
     1539                          &hdr->other_param); 
    14051540    } 
    14061541} 
    14071542 
    14081543/* Parse Record-Route header. */ 
    1409 PJ_DEF(pjsip_rr_hdr*) parse_hdr_rr( pj_scanner *scanner, pj_pool_t *pool) 
     1544static pjsip_hdr* parse_hdr_rr( pjsip_parse_ctx *ctx) 
    14101545{ 
    14111546    pjsip_rr_hdr *first = NULL; 
     1547    pj_scanner *scanner = ctx->scanner; 
    14121548 
    14131549    do { 
    1414         pjsip_rr_hdr *hdr = pjsip_rr_hdr_create(pool); 
     1550        pjsip_rr_hdr *hdr = pjsip_rr_hdr_create(ctx->pool); 
    14151551        if (!first) { 
    14161552            first = hdr; 
     
    14181554            pj_list_insert_before(first, hdr); 
    14191555        } 
    1420         parse_hdr_rr_route(scanner, pool, hdr); 
    1421         if (*scanner->current == ',') { 
     1556        parse_hdr_rr_route(scanner, ctx->pool, hdr); 
     1557        if (*scanner->curptr == ',') { 
    14221558            pj_scan_get_char(scanner); 
    14231559        } else { 
     
    14261562    } while (1); 
    14271563    parse_hdr_end(scanner); 
    1428     return first; 
     1564 
     1565    if (ctx->rdata && ctx->rdata->record_route==NULL) 
     1566        ctx->rdata->record_route = first; 
     1567 
     1568    return (pjsip_hdr*)first; 
    14291569} 
    14301570 
    14311571/* Parse Route: header. */ 
    1432 PJ_DEF(pjsip_route_hdr*) parse_hdr_route( pj_scanner *scanner,  
    1433                                           pj_pool_t *pool) 
     1572static pjsip_hdr* parse_hdr_route( pjsip_parse_ctx *ctx ) 
    14341573{ 
    14351574    pjsip_route_hdr *first = NULL; 
     1575    pj_scanner *scanner = ctx->scanner; 
    14361576 
    14371577    do { 
    1438         pjsip_route_hdr *hdr = pjsip_route_hdr_create(pool); 
     1578        pjsip_route_hdr *hdr = pjsip_route_hdr_create(ctx->pool); 
    14391579        if (!first) { 
    14401580            first = hdr; 
     
    14421582            pj_list_insert_before(first, hdr); 
    14431583        } 
    1444         parse_hdr_rr_route(scanner, pool, hdr); 
    1445         if (*scanner->current == ',') { 
     1584        parse_hdr_rr_route(scanner, ctx->pool, hdr); 
     1585        if (*scanner->curptr == ',') { 
    14461586            pj_scan_get_char(scanner); 
    14471587        } else { 
     
    14501590    } while (1); 
    14511591    parse_hdr_end(scanner); 
    1452     return first; 
     1592 
     1593    if (ctx->rdata && ctx->rdata->route==NULL) 
     1594        ctx->rdata->route = first; 
     1595 
     1596    return (pjsip_hdr*)first; 
    14531597} 
    14541598 
    14551599/* Parse Via: header. */ 
    1456 PJ_DEF(pjsip_via_hdr*) parse_hdr_via( pj_scanner *scanner, pj_pool_t *pool) 
     1600static pjsip_hdr* parse_hdr_via( pjsip_parse_ctx *ctx ) 
    14571601{ 
    14581602    pjsip_via_hdr *first = NULL; 
     1603    pj_scanner *scanner = ctx->scanner; 
    14591604 
    14601605    do { 
    1461         pjsip_via_hdr *hdr = pjsip_via_hdr_create(pool); 
     1606        pjsip_via_hdr *hdr = pjsip_via_hdr_create(ctx->pool); 
    14621607        if (!first) 
    14631608            first = hdr; 
     
    14701615        pj_scan_advance_n( scanner, 8, 1); 
    14711616 
    1472         pj_scan_get( scanner, pjsip_TOKEN_SPEC, &hdr->transport); 
    1473         pj_scan_get( scanner, pjsip_HOST_SPEC, &hdr->sent_by.host); 
    1474  
    1475         if (*scanner->current==':') { 
     1617        pj_scan_get( scanner, &pjsip_TOKEN_SPEC, &hdr->transport); 
     1618        pj_scan_get( scanner, &pjsip_HOST_SPEC, &hdr->sent_by.host); 
     1619 
     1620        if (*scanner->curptr==':') { 
    14761621            pj_str_t digit; 
    14771622            pj_scan_get_char(scanner); 
    1478             pj_scan_get(scanner, pjsip_DIGIT_SPEC, &digit); 
     1623            pj_scan_get(scanner, &pjsip_DIGIT_SPEC, &digit); 
    14791624            hdr->sent_by.port = pj_strtoul(&digit); 
    14801625        } else { 
     
    14821627        } 
    14831628         
    1484         int_parse_via_param(hdr, scanner, pool); 
    1485  
    1486         if (*scanner->current == '(') { 
     1629        int_parse_via_param(hdr, scanner, ctx->pool); 
     1630 
     1631        if (*scanner->curptr == '(') { 
    14871632            pj_scan_get_char(scanner); 
    14881633            pj_scan_get_until_ch( scanner, ')', &hdr->comment); 
     
    14901635        } 
    14911636 
    1492         if (*scanner->current != ',') 
     1637        if (*scanner->curptr != ',') 
    14931638            break; 
    14941639 
     
    14981643 
    14991644    parse_hdr_end(scanner); 
    1500     return first; 
     1645 
     1646    if (ctx->rdata && ctx->rdata->via == NULL) 
     1647        ctx->rdata->via = first; 
     1648 
     1649    return (pjsip_hdr*)first; 
    15011650} 
    15021651 
    15031652/* Parse generic header. */ 
    1504 PJ_DEF(pjsip_generic_string_hdr*) parse_hdr_generic_string( pj_scanner *scanner,  
    1505                                                 pj_pool_t *pool) 
     1653static pjsip_hdr* parse_hdr_generic_string( pjsip_parse_ctx *ctx ) 
    15061654{ 
    15071655    pjsip_generic_string_hdr *hdr; 
    15081656 
    1509     hdr = pjsip_generic_string_hdr_create(pool, NULL); 
    1510     parse_generic_string_hdr(hdr, scanner); 
    1511     return hdr; 
     1657    hdr = pjsip_generic_string_hdr_create(ctx->pool, NULL); 
     1658    parse_generic_string_hdr(hdr, ctx->scanner); 
     1659    return (pjsip_hdr*)hdr; 
    15121660 
    15131661} 
     
    15191667    pj_scanner scanner; 
    15201668    pjsip_hdr *hdr = NULL; 
     1669    pjsip_parse_ctx context; 
    15211670    PJ_USE_EXCEPTION; 
    15221671 
    15231672    init_sip_parser(); 
    15241673 
    1525     pj_scan_init(&scanner, buf, size, PJ_SCAN_AUTOSKIP_WS_HEADER, &on_syntax_error); 
     1674    pj_scan_init(&scanner, buf, size, PJ_SCAN_AUTOSKIP_WS_HEADER,  
     1675                 &on_syntax_error); 
     1676 
     1677    context.scanner = &scanner; 
     1678    context.pool = pool; 
     1679    context.rdata = NULL; 
    15261680 
    15271681    PJ_TRY { 
    15281682        pjsip_parse_hdr_func *handler = find_handler(hname); 
    15291683        if (handler) { 
    1530             hdr = (*handler)(&scanner, pool); 
     1684            hdr = (*handler)(&context); 
    15311685        } else { 
    1532             pjsip_generic_string_hdr *ghdr = parse_hdr_generic_string(&scanner, pool); 
    1533             ghdr->type = PJSIP_H_OTHER; 
    1534             pj_strdup(pool, &ghdr->name, hname); 
    1535             ghdr->sname = ghdr->name; 
    1536             hdr = (pjsip_hdr*)ghdr; 
     1686            hdr = parse_hdr_generic_string(&context); 
     1687            hdr->type = PJSIP_H_OTHER; 
     1688            pj_strdup(pool, &hdr->name, hname); 
     1689            hdr->sname = hdr->name; 
    15371690        } 
    15381691 
     
    15441697 
    15451698    if (parsed_len) { 
    1546         *parsed_len = (scanner.current - scanner.begin); 
     1699        *parsed_len = (scanner.curptr - scanner.begin); 
    15471700    } 
    15481701 
Note: See TracChangeset for help on using the changeset viewer.