Changeset 1959
- Timestamp:
- May 17, 2008 12:45:00 PM (16 years ago)
- Location:
- pjproject/trunk
- Files:
-
- 1 added
- 9 edited
Legend:
- Unmodified
- Added
- Removed
-
pjproject/trunk/pjlib/build/pjlib_test.vcproj
r898 r1959 209 209 > 210 210 <File 211 RelativePath="..\src\pjlib-test\activesock.c" 212 > 213 </File> 214 <File 211 215 RelativePath="..\src\pjlib-test\atomic.c" 212 216 > -
pjproject/trunk/pjsip/build/Makefile
r1818 r1959 87 87 export TEST_SRCDIR = ../src/test-pjsip 88 88 export TEST_OBJS += dlg_core_test.o dns_test.o msg_err_test.o \ 89 msg_logger.o msg_test.o \89 msg_logger.o msg_test.o regc_test.o \ 90 90 test.o transport_loop_test.o transport_tcp_test.o \ 91 91 transport_test.o transport_udp_test.o \ -
pjproject/trunk/pjsip/build/test_pjsip.dsp
r1610 r1959 118 118 # Begin Source File 119 119 120 SOURCE="..\src\test-pjsip\regc_test.c" 121 # End Source File 122 # Begin Source File 123 120 124 SOURCE="..\src\test-pjsip\test.c" 121 125 # End Source File -
pjproject/trunk/pjsip/build/test_pjsip.vcproj
r1469 r1959 348 348 </File> 349 349 <File 350 RelativePath="..\src\test-pjsip\regc_test.c" 351 > 352 </File> 353 <File 350 354 RelativePath="..\src\test-pjsip\test.c" 351 355 > -
pjproject/trunk/pjsip/include/pjsip-ua/sip_regc.h
r1748 r1959 63 63 { 64 64 pjsip_regc *regc; /**< Client registration structure. */ 65 void *token; /**< Arbitrary token. */ 66 pj_status_t status; /**< Error status. */ 65 void *token; /**< Arbitrary token set by application */ 66 67 /** Error status. If this value is non-PJ_SUCCESS, some error has occured. 68 * Note that even when this contains PJ_SUCCESS the registration might 69 * have failed; in this case the \a code field will contain non 70 * successful (non-2xx status class) code 71 */ 72 pj_status_t status; 67 73 int code; /**< SIP status code received. */ 68 74 pj_str_t reason; /**< SIP reason phrase received. */ … … 296 302 297 303 /** 298 * Update Contact details in the client registration structure. 304 * Update Contact details in the client registration structure. For each 305 * contact URI, if the uri is not found in existing contact, it will be 306 * added to the Contact list. If the URI matches existing contact, nothing 307 * will be added. This function will also mark existing contacts which 308 * are not specified in the new contact list as to be removed, by adding 309 * "expires=0" parameter to these contacts. 310 * 311 * Once the contact list has been updated, application must update the 312 * registration by creating a new REGISTER request and send it to the 313 * registrar. This request will contain both old and new contacts; the 314 * old contacts will have it's expires parameter set to zero to instruct 315 * the registrar to remove the bindings. 299 316 * 300 317 * @param regc The client registration structure. 301 318 * @param ccnt Number of contacts. 302 * @param contact Array of contact s.303 * @return zeroif sucessfull.319 * @param contact Array of contact URIs. 320 * @return PJ_SUCCESS if sucessfull. 304 321 */ 305 322 PJ_DECL(pj_status_t) pjsip_regc_update_contact( pjsip_regc *regc, … … 308 325 309 326 /** 310 * Update the expires value. 327 * Update the expires value. The next REGISTER request will contain 328 * new expires value for the registration. 311 329 * 312 330 * @param regc The client registration structure. -
pjproject/trunk/pjsip/include/pjsip/sip_config.h
r1857 r1959 109 109 /** 110 110 * Specify whether client registration should check for its 111 * registered contact in Contact header of successful REGISTE 111 * registered contact in Contact header of successful REGISTER 112 112 * response to determine whether registration has been successful. 113 113 * This setting may be disabled if non-compliant registrar is unable … … 118 118 pj_bool_t check_contact; 119 119 120 /** 121 * Specify whether client registration should add "x-uid" extension 122 * parameter in all Contact URIs that it registers to assist the 123 * matching of Contact URIs in the 200/OK REGISTER response, in 124 * case the registrar is unable to return exact Contact URI in the 125 * 200/OK response. 126 * 127 * Default is PJSIP_REGISTER_CLIENT_ADD_XUID_PARAM. 128 */ 129 pj_bool_t add_xuid_param; 130 120 131 } regc; 121 132 … … 714 725 #endif 715 726 716 PJ_END_DECL 727 728 /** 729 * Specify the number of seconds to refresh the client registration 730 * before the registration expires. 731 * 732 * Default: 5 seconds 733 */ 734 #ifndef PJSIP_REGISTER_CLIENT_DELAY_BEFORE_REFRESH 735 # define PJSIP_REGISTER_CLIENT_DELAY_BEFORE_REFRESH 5 736 #endif 737 717 738 718 739 /** … … 722 743 * if non-compliant registrar is unable to return correct Contact header. 723 744 * 724 * This setting can be changed in run-time with using pjsip_cfg(). 745 * This setting can be changed in run-time by settting \a regc.check_contact 746 * field of pjsip_cfg(). 725 747 * 726 748 * Default is 1 … … 732 754 733 755 /** 756 * Specify whether client registration should add "x-uid" extension 757 * parameter in all Contact URIs that it registers to assist the 758 * matching of Contact URIs in the 200/OK REGISTER response, in 759 * case the registrar is unable to return exact Contact URI in the 760 * 200/OK response. 761 * 762 * This setting can be changed in run-time by setting 763 * \a regc.add_xuid_param field of pjsip_cfg(). 764 * 765 * Default is 0. 766 */ 767 #ifndef PJSIP_REGISTER_CLIENT_ADD_XUID_PARAM 768 # define PJSIP_REGISTER_CLIENT_ADD_XUID_PARAM 0 769 #endif 770 771 772 PJ_END_DECL 773 774 /** 734 775 * @} 735 776 */ -
pjproject/trunk/pjsip/src/pjsip-ua/sip_reg.c
r1946 r1959 36 36 37 37 #define REFRESH_TIMER 1 38 #define DELAY_BEFORE_REFRESH 538 #define DELAY_BEFORE_REFRESH PJSIP_REGISTER_CLIENT_DELAY_BEFORE_REFRESH 39 39 #define THIS_FILE "sip_reg.c" 40 40 … … 44 44 #define REGC_TSX_TIMEOUT 33000 45 45 46 enum { NOEXP = 0x1FFFFFFF }; 47 48 static const pj_str_t XUID_PARAM_NAME = { "x-uid", 5 }; 49 50 51 /* Current/pending operation */ 52 enum regc_op 53 { 54 REGC_IDLE, 55 REGC_REGISTERING, 56 REGC_UNREGISTERING 57 }; 46 58 47 59 /** … … 55 67 pj_bool_t has_tsx; 56 68 pj_int32_t busy; 69 enum regc_op current_op; 70 71 pj_bool_t add_xuid_param; 57 72 58 73 void *token; … … 66 81 pjsip_from_hdr *from_hdr; 67 82 pjsip_to_hdr *to_hdr; 68 pjsip_hdr contact_hdr_list; 83 pjsip_contact_hdr contact_hdr_list; 84 pjsip_contact_hdr removed_contact_hdr_list; 69 85 pjsip_expires_hdr *expires_hdr; 70 pjsip_contact_hdr *unreg_contact_hdr;71 pjsip_expires_hdr *unreg_expires_hdr;72 86 pj_uint32_t expires; 73 87 pjsip_route_hdr route_set; … … 93 107 94 108 95 96 109 PJ_DEF(pj_status_t) pjsip_regc_create( pjsip_endpoint *endpt, void *token, 97 110 pjsip_regc_cb *cb, … … 115 128 regc->cb = cb; 116 129 regc->expires = PJSIP_REGC_EXPIRATION_NOT_SPECIFIED; 130 regc->add_xuid_param = pjsip_cfg()->regc.add_xuid_param; 117 131 118 132 status = pjsip_auth_clt_init(®c->auth_sess, endpt, regc->pool, 0); … … 123 137 pj_list_init(®c->hdr_list); 124 138 pj_list_init(®c->contact_hdr_list); 139 pj_list_init(®c->removed_contact_hdr_list); 125 140 126 141 /* Done */ … … 142 157 pjsip_transport_dec_ref(regc->last_transport); 143 158 regc->last_transport = NULL; 159 } 160 if (regc->timer.id != 0) { 161 pjsip_endpt_cancel_timer(regc->endpt, ®c->timer); 162 regc->timer.id = 0; 144 163 } 145 164 pjsip_endpt_release_pool(regc->endpt, regc->pool); … … 200 219 { 201 220 const pj_str_t CONTACT = { "Contact", 7 }; 221 pjsip_contact_hdr *h; 202 222 int i; 203 223 204 /* Clear existing contacts */ 205 pj_list_init(®c->contact_hdr_list); 206 224 /* Save existing contact list to removed_contact_hdr_list and 225 * clear contact_hdr_list. 226 */ 227 pj_list_merge_last(®c->removed_contact_hdr_list, 228 ®c->contact_hdr_list); 229 230 /* Set the expiration of Contacts in to removed_contact_hdr_list 231 * zero. 232 */ 233 h = regc->removed_contact_hdr_list.next; 234 while (h != ®c->removed_contact_hdr_list) { 235 h->expires = 0; 236 h = h->next; 237 } 238 239 /* Process new contacts */ 207 240 for (i=0; i<contact_cnt; ++i) { 208 pjsip_ hdr *hdr;241 pjsip_contact_hdr *hdr; 209 242 pj_str_t tmp; 210 243 211 244 pj_strdup_with_null(regc->pool, &tmp, &contact[i]); 212 hdr = (pjsip_ hdr*)245 hdr = (pjsip_contact_hdr*) 213 246 pjsip_parse_hdr(regc->pool, &CONTACT, tmp.ptr, tmp.slen, NULL); 214 247 if (hdr == NULL) { … … 216 249 (int)tmp.slen, tmp.ptr)); 217 250 return PJSIP_EINVALIDURI; 251 } 252 253 /* Find the new contact in old contact list. If found, remove 254 * the old header from the old header list. 255 */ 256 h = regc->removed_contact_hdr_list.next; 257 while (h != ®c->removed_contact_hdr_list) { 258 int rc; 259 260 rc = pjsip_uri_cmp(PJSIP_URI_IN_CONTACT_HDR, 261 h->uri, hdr->uri); 262 if (rc == 0) { 263 /* Match */ 264 pj_list_erase(h); 265 break; 266 } 267 268 h = h->next; 269 } 270 271 /* If add_xuid_param option is enabled and Contact URI is sip/sips, 272 * add xuid parameter to assist matching the Contact URI in the 273 * REGISTER response later. 274 */ 275 if (regc->add_xuid_param && (PJSIP_URI_SCHEME_IS_SIP(hdr->uri) || 276 PJSIP_URI_SCHEME_IS_SIPS(hdr->uri))) 277 { 278 pjsip_param *xuid_param; 279 pjsip_sip_uri *sip_uri; 280 281 xuid_param = PJ_POOL_ZALLOC_T(regc->pool, pjsip_param); 282 xuid_param->name = XUID_PARAM_NAME; 283 pj_create_unique_string(regc->pool, &xuid_param->value); 284 285 sip_uri = pjsip_uri_get_uri(hdr->uri); 286 pj_list_push_back(&sip_uri->other_param, xuid_param); 218 287 } 219 288 … … 288 357 regc->cseq_hdr->cseq = pj_rand() % 0xFFFF; 289 358 pjsip_method_set( ®c->cseq_hdr->method, PJSIP_REGISTER_METHOD); 290 291 /* Create "Contact" header used in unregistration. */292 regc->unreg_contact_hdr = pjsip_contact_hdr_create(regc->pool);293 regc->unreg_contact_hdr->star = 1;294 295 /* Create "Expires" header used in unregistration. */296 regc->unreg_expires_hdr = pjsip_expires_hdr_create( regc->pool, 0);297 359 298 360 /* Done. */ … … 437 499 { 438 500 pjsip_msg *msg; 439 pjsip_ hdr *hdr;501 pjsip_contact_hdr *hdr; 440 502 pj_status_t status; 441 503 pjsip_tx_data *tdata; … … 457 519 } 458 520 521 /* Also add bindings which are to be removed */ 522 while (!pj_list_empty(®c->removed_contact_hdr_list)) { 523 hdr = regc->removed_contact_hdr_list.next; 524 pjsip_msg_add_hdr(msg, (pjsip_hdr*) 525 pjsip_hdr_clone(tdata->pool, hdr)); 526 pj_list_erase(hdr); 527 } 528 529 459 530 if (regc->expires_hdr) 460 531 pjsip_msg_add_hdr(msg, (pjsip_hdr*) … … 497 568 498 569 /* Add Contact headers. */ 499 hdr = regc->contact_hdr_list.next;500 while (hdr != ®c->contact_hdr_list) {570 hdr = (pjsip_hdr*)regc->contact_hdr_list.next; 571 while (hdr != (pjsip_hdr*)®c->contact_hdr_list) { 501 572 pjsip_msg_add_hdr(msg, (pjsip_hdr*) 502 573 pjsip_hdr_shallow_clone(tdata->pool, hdr)); … … 504 575 } 505 576 506 pjsip_msg_add_hdr( msg, (pjsip_hdr*)regc->unreg_expires_hdr); 577 /* Also add bindings which are to be removed */ 578 while (!pj_list_empty(®c->removed_contact_hdr_list)) { 579 hdr = (pjsip_hdr*)regc->removed_contact_hdr_list.next; 580 pjsip_msg_add_hdr(msg, (pjsip_hdr*) 581 pjsip_hdr_clone(tdata->pool, hdr)); 582 pj_list_erase(hdr); 583 } 584 585 /* Add Expires:0 header */ 586 hdr = (pjsip_hdr*) pjsip_expires_hdr_create(tdata->pool, 0); 587 pjsip_msg_add_hdr(msg, hdr); 507 588 508 589 *p_tdata = tdata; … … 514 595 { 515 596 pjsip_tx_data *tdata; 597 pjsip_contact_hdr *hcontact; 598 pjsip_hdr *hdr; 516 599 pjsip_msg *msg; 517 600 pj_status_t status; … … 529 612 530 613 msg = tdata->msg; 531 pjsip_msg_add_hdr( msg, (pjsip_hdr*)regc->unreg_contact_hdr); 532 pjsip_msg_add_hdr( msg, (pjsip_hdr*)regc->unreg_expires_hdr); 614 615 /* Clear removed_contact_hdr_list */ 616 pj_list_init(®c->removed_contact_hdr_list); 617 618 /* Add Contact:* header */ 619 hcontact = pjsip_contact_hdr_create(tdata->pool); 620 hcontact->star = 1; 621 pjsip_msg_add_hdr(msg, (pjsip_hdr*)hcontact); 622 623 /* Add Expires:0 header */ 624 hdr = (pjsip_hdr*) pjsip_expires_hdr_create(tdata->pool, 0); 625 pjsip_msg_add_hdr(msg, hdr); 533 626 534 627 *p_tdata = tdata; … … 616 709 } 617 710 711 static pj_int32_t calculate_response_expiration(const pjsip_regc *regc, 712 const pjsip_rx_data *rdata, 713 unsigned *contact_cnt, 714 unsigned max_contact, 715 pjsip_contact_hdr *contacts[]) 716 { 717 pj_int32_t expiration = NOEXP; 718 const pjsip_msg *msg = rdata->msg_info.msg; 719 const pjsip_hdr *hdr; 720 721 /* Enumerate all Contact headers in the response */ 722 *contact_cnt = 0; 723 for (hdr=msg->hdr.next; hdr!=&msg->hdr; hdr=hdr->next) { 724 if (hdr->type == PJSIP_H_CONTACT && 725 *contact_cnt < max_contact) 726 { 727 contacts[*contact_cnt] = (pjsip_contact_hdr*)hdr; 728 ++(*contact_cnt); 729 } 730 } 731 732 if (regc->current_op == REGC_REGISTERING) { 733 pj_bool_t has_our_contact = PJ_FALSE; 734 const pjsip_expires_hdr *expires; 735 736 /* Get Expires header */ 737 expires = (const pjsip_expires_hdr*) 738 pjsip_msg_find_hdr(msg, PJSIP_H_EXPIRES, NULL); 739 740 /* Try to find the Contact URIs that we register, in the response 741 * to get the expires value. We'll try both with comparing the URI 742 * and comparing the extension param only. 743 */ 744 if (pjsip_cfg()->regc.check_contact || regc->add_xuid_param) { 745 unsigned i; 746 for (i=0; i<*contact_cnt; ++i) { 747 const pjsip_contact_hdr *our_hdr; 748 749 our_hdr = (const pjsip_contact_hdr*) 750 regc->contact_hdr_list.next; 751 752 /* Match with our Contact header(s) */ 753 while ((void*)our_hdr != (void*)®c->contact_hdr_list) { 754 755 const pjsip_uri *uri1, *uri2; 756 pj_bool_t matched = PJ_FALSE; 757 758 /* Exclude the display name when comparing the URI 759 * since server may not return it. 760 */ 761 uri1 = (const pjsip_uri*) 762 pjsip_uri_get_uri(contacts[i]->uri); 763 uri2 = (const pjsip_uri*) 764 pjsip_uri_get_uri(our_hdr->uri); 765 766 /* First try with exact matching, according to RFC 3261 767 * Section 19.1.4 URI Comparison 768 */ 769 if (pjsip_cfg()->regc.check_contact) { 770 matched = pjsip_uri_cmp(PJSIP_URI_IN_CONTACT_HDR, 771 uri1, uri2)==0; 772 } 773 774 /* If no match is found, try with matching the extension 775 * parameter only if extension parameter was added. 776 */ 777 if (!matched && regc->add_xuid_param && 778 (PJSIP_URI_SCHEME_IS_SIP(uri1) || 779 PJSIP_URI_SCHEME_IS_SIPS(uri1)) && 780 (PJSIP_URI_SCHEME_IS_SIP(uri2) || 781 PJSIP_URI_SCHEME_IS_SIPS(uri2))) 782 { 783 const pjsip_sip_uri *sip_uri1, *sip_uri2; 784 const pjsip_param *p1, *p2; 785 786 sip_uri1 = (const pjsip_sip_uri*)uri1; 787 sip_uri2 = (const pjsip_sip_uri*)uri2; 788 789 p1 = pjsip_param_cfind(&sip_uri1->other_param, 790 &XUID_PARAM_NAME); 791 p2 = pjsip_param_cfind(&sip_uri2->other_param, 792 &XUID_PARAM_NAME); 793 matched = p1 && p2 && 794 pj_strcmp(&p1->value, &p2->value)==0; 795 796 } 797 798 if (matched) { 799 has_our_contact = PJ_TRUE; 800 801 if (contacts[i]->expires >= 0 && 802 contacts[i]->expires < expiration) 803 { 804 /* Get the lowest expiration time. */ 805 expiration = contacts[i]->expires; 806 } 807 808 break; 809 } 810 811 our_hdr = our_hdr->next; 812 813 } /* while ((void.. */ 814 815 } /* for (i=.. */ 816 817 /* If matching Contact header(s) are found but the 818 * header doesn't contain expires parameter, get the 819 * expiration value from the Expires header. And 820 * if Expires header is not present, get the expiration 821 * value from the request. 822 */ 823 if (has_our_contact && expiration == NOEXP) { 824 if (expires) { 825 expiration = expires->ivalue; 826 } else if (regc->expires_hdr) { 827 expiration = regc->expires_hdr->ivalue; 828 } else { 829 /* We didn't request explicit expiration value, 830 * and server doesn't specify it either. This 831 * shouldn't happen unless we have a broken 832 * registrar. 833 */ 834 expiration = 3600; 835 } 836 } 837 838 } 839 840 /* If we still couldn't get matching Contact header(s), it means 841 * there must be something wrong with the registrar (e.g. it may 842 * have modified the URI's in the response, which is prohibited). 843 */ 844 if (expiration==NOEXP) { 845 /* If the number of Contact headers in the response matches 846 * ours, they're all probably ours. Get the expiration 847 * from there if this is the case, or from Expires header 848 * if we don't have exact Contact header count, or 849 * from the request as the last resort. 850 */ 851 unsigned our_contact_cnt; 852 853 our_contact_cnt = pj_list_size(®c->contact_hdr_list); 854 855 if (*contact_cnt == our_contact_cnt && *contact_cnt && 856 contacts[0]->expires >= 0) 857 { 858 expiration = contacts[0]->expires; 859 } else if (expires) 860 expiration = expires->ivalue; 861 else if (regc->expires_hdr) 862 expiration = regc->expires_hdr->ivalue; 863 else 864 expiration = 3600; 865 } 866 867 } else { 868 /* Just assume that the unregistration has been successful. */ 869 expiration = 0; 870 } 871 872 /* Must have expiration value by now */ 873 pj_assert(expiration != NOEXP); 874 875 return expiration; 876 } 877 618 878 static void tsx_callback(void *token, pjsip_event *event) 619 879 { … … 645 905 pjsip_rx_data *rdata = event->body.tsx_state.src.rdata; 646 906 pjsip_tx_data *tdata; 907 908 /* reset current op */ 909 regc->current_op = REGC_IDLE; 647 910 648 911 status = pjsip_auth_clt_reinit_req( ®c->auth_sess, … … 683 946 */ 684 947 685 /* Nothing to do*/686 ;948 /* Just reset current op */ 949 regc->current_op = REGC_IDLE; 687 950 688 951 } else { 689 int contact_cnt = 0; 952 pjsip_rx_data *rdata; 953 pj_int32_t expiration = NOEXP; 954 unsigned contact_cnt = 0; 690 955 pjsip_contact_hdr *contact[PJSIP_REGC_MAX_CONTACT]; 691 pjsip_rx_data *rdata;692 enum { NOEXP = 0x1FFFFFFF };693 pj_int32_t expiration = NOEXP;694 956 695 957 if (tsx->status_code/100 == 2) { 696 int i;697 pjsip_contact_hdr *hdr;698 pjsip_msg *msg;699 pj_bool_t has_our_contact = PJ_FALSE;700 pjsip_expires_hdr *expires;701 958 702 959 rdata = event->body.tsx_state.src.rdata; 703 msg = rdata->msg_info.msg; 704 705 /* Record all Contact headers in the response */ 706 hdr = (pjsip_contact_hdr*) 707 pjsip_msg_find_hdr( msg, PJSIP_H_CONTACT, NULL); 708 while (hdr) { 709 contact[contact_cnt++] = hdr; 710 hdr = hdr->next; 711 if (hdr == (void*)&msg->hdr) 712 break; 713 hdr = (pjsip_contact_hdr*) 714 pjsip_msg_find_hdr(msg, PJSIP_H_CONTACT, hdr); 715 } 716 717 /* Set default expiration value to the value of Expires hdr */ 718 expires = (pjsip_expires_hdr*) 719 pjsip_msg_find_hdr(msg, PJSIP_H_EXPIRES, NULL); 720 721 if (expires) 722 expiration = expires->ivalue; 723 724 /* Enumerate all Contact headers found in the response and 725 * find the Contact(s) that we register. 726 * 727 * Note: 728 * by default we require that the exact same URI that we 729 * register is returned in the 200/OK response (by exact, 730 * meaning all URI components including transport param), 731 * otherwise if we don't detect that our URI is there, we 732 * treat registration as failed. 733 * 734 * If your registrar server couldn't do this, you can 735 * disable this exact URI checking. See the compile time 736 * setting PJSIP_REGISTER_CLIENT_CHECK_CONTACT or the 737 * corresponding run-time setting in pjsip_cfg(). 738 */ 739 for (i=0; i<contact_cnt && pjsip_cfg()->regc.check_contact; ++i) { 740 pjsip_contact_hdr *our_contact; 741 742 our_contact = (pjsip_contact_hdr*) 743 regc->contact_hdr_list.next; 744 745 while ((void*)our_contact != (void*)®c->contact_hdr_list) { 746 747 const pjsip_uri *uri1, *uri2; 748 749 /* Compare URIs. 750 * Exclude the display name when comparing the URI since 751 * server may not return it. 752 */ 753 754 uri1=(const pjsip_uri*)pjsip_uri_get_uri(contact[i]->uri); 755 uri2=(const pjsip_uri*)pjsip_uri_get_uri(our_contact->uri); 756 if (pjsip_uri_cmp(PJSIP_URI_IN_CONTACT_HDR, uri1, uri2)==0) 757 { 758 has_our_contact = PJ_TRUE; 759 760 if (contact[i]->expires >= 0 && 761 contact[i]->expires < expiration) 762 { 763 /* Get the lowest expiration time. */ 764 expiration = contact[i]->expires; 765 } 766 } 767 768 our_contact = our_contact->next; 769 } 770 } 771 772 /* If regc.check_contact is disabled, and no Expires header 773 * has been found, but the server does return one single 774 * Contact header, assumes that the server is broken/unable to 775 * return the correct Contact. In this case, get the expiration 776 * from the single Contact header in the response. 777 */ 778 if (expiration==NOEXP && !pjsip_cfg()->regc.check_contact && 779 contact_cnt==1) 780 { 781 if (contact[0]->expires >= 0) 782 expiration = contact[0]->expires; 783 } 784 785 /* When the response doesn't contain our Contact header, that 786 * means we have been unregistered. 787 */ 788 if (pjsip_cfg()->regc.check_contact && !has_our_contact) 789 expiration = 0; 960 961 /* Calculate expiration */ 962 expiration = calculate_response_expiration(regc, rdata, 963 &contact_cnt, 964 PJSIP_REGC_MAX_CONTACT, 965 contact); 966 967 /* Mark operation as complete */ 968 regc->current_op = REGC_IDLE; 790 969 791 970 /* Schedule next registration */ 792 if (regc->auto_reg && expiration != 0 && expiration != NOEXP) {971 if (regc->auto_reg && expiration > 0) { 793 972 pj_time_val delay = { 0, 0}; 794 973 … … 820 999 ++regc->busy; 821 1000 1001 /* Update registration */ 1002 if (expiration==NOEXP) expiration=-1; 1003 regc->expires = expiration; 1004 822 1005 /* Call callback. */ 823 if (expiration == NOEXP) expiration = -1;824 1006 call_callback(regc, PJ_SUCCESS, tsx->status_code, 825 1007 (rdata ? &rdata->msg_info.msg->line.status.reason … … 842 1024 pj_status_t status; 843 1025 pjsip_cseq_hdr *cseq_hdr; 1026 pjsip_expires_hdr *expires_hdr; 844 1027 pj_uint32_t cseq; 845 1028 … … 852 1035 } 853 1036 1037 pj_assert(regc->current_op == REGC_IDLE); 1038 854 1039 /* Invalidate message buffer. */ 855 1040 pjsip_tx_data_invalidate_msg(tdata); … … 861 1046 cseq_hdr->cseq = cseq; 862 1047 1048 /* Find Expires header */ 1049 expires_hdr = (pjsip_expires_hdr*) 1050 pjsip_msg_find_hdr(tdata->msg, PJSIP_H_EXPIRES, NULL); 1051 863 1052 /* Bind to transport selector */ 864 1053 pjsip_tx_data_set_transport(tdata, ®c->tp_sel); … … 869 1058 regc->has_tsx = PJ_TRUE; 870 1059 ++regc->busy; 1060 1061 /* Set current operation based on the value of Expires header */ 1062 if (expires_hdr && expires_hdr->ivalue==0) 1063 regc->current_op = REGC_UNREGISTERING; 1064 else 1065 regc->current_op = REGC_REGISTERING; 1066 871 1067 status = pjsip_endpt_send_request(regc->endpt, tdata, REGC_TSX_TIMEOUT, 872 1068 regc, &tsx_callback); -
pjproject/trunk/pjsip/src/test-pjsip/test.c
r1469 r1959 360 360 #endif 361 361 362 #if INCLUDE_REGC_TEST 363 DO_TEST(regc_test()); 364 #endif 365 362 366 363 367 on_return: -
pjproject/trunk/pjsip/src/test-pjsip/test.h
r1610 r1959 41 41 #define INCLUDE_TSX_GROUP 1 42 42 #define INCLUDE_INV_GROUP 1 43 #define INCLUDE_REGC_GROUP 1 43 44 44 45 #define INCLUDE_BENCHMARKS 1 … … 63 64 #define INCLUDE_TSX_TEST INCLUDE_TSX_GROUP 64 65 #define INCLUDE_INV_OA_TEST INCLUDE_INV_GROUP 66 #define INCLUDE_REGC_TEST INCLUDE_REGC_GROUP 65 67 66 68 … … 75 77 int transport_tcp_test(void); 76 78 int resolve_test(void); 79 int regc_test(void); 77 80 78 81 struct tsx_test_param
Note: See TracChangeset
for help on using the changeset viewer.