Browse code

Currently, SER matches E2E ACKs only if there is an equality between From HF in INVITE and ACK. While this is pretty safe, there are UAs that do mess small things, like display name, or some bigger ones, like URI, in generated ACK. However, matching over the full URI (or worse, HF) is not needed and was even intended for deprecation (see 1st comment of 3261#Sec. 12.2.1.1). The applied patch should boost a bit the matching flexibility - only compare the tag.

Closes #SER-419.

Bogdan Pintea authored on 04/01/2009 15:27:39
Showing 2 changed files
... ...
@@ -77,7 +77,10 @@ modules:
77 77
  - blst      - new module containing script blacklist manipulations functions
78 78
                (the source of a message can be blacklisted, removed from the
79 79
                 blacklist or checked for presence in the blacklist).
80
- - tm        - added t_reset_fr(), t_reset_retr(), t_reset_max_lifetime()
80
+ - tm        - matching of E2E ACKs no longer requires full From HF identity,
81
+               but rather only tag equality (this behaviour can be changed by
82
+               defining TM_E2E_ACK_CHECK_FROM_URI)
83
+             - added t_reset_fr(), t_reset_retr(), t_reset_max_lifetime()
81 84
              - t_relay_to renamed to t_relay_to_avp (undocumented function)
82 85
              - t_relay() can now also take host and port parameters (e.g.
83 86
                t_relay(host, port)), behaving like a statefull 
... ...
@@ -605,19 +605,34 @@ int t_lookup_request( struct sip_msg* p_msg , int leave_new_locked,
605 605
 			/* CSeq only the number without method ! */
606 606
 			if (get_cseq(t_msg)->number.len!=get_cseq(p_msg)->number.len)
607 607
 				continue;
608
-			if (! EQ_LEN(from)) continue;
609 608
 			/* To only the uri -- to many UACs screw up tags  */
610 609
 			if (get_to(t_msg)->uri.len!=get_to(p_msg)->uri.len)
611 610
 				continue;
612 611
 			if (!EQ_STR(callid)) continue;
613 612
 			if (memcmp(get_cseq(t_msg)->number.s, get_cseq(p_msg)->number.s,
614 613
 				get_cseq(p_msg)->number.len)!=0) continue;
615
-			if (!EQ_STR(from)) continue;
616 614
 			if (memcmp(get_to(t_msg)->uri.s, get_to(p_msg)->uri.s,
617 615
 				get_to(t_msg)->uri.len)!=0) continue;
618 616
 			
619 617
 			/* it is e2e ACK/200 */
620 618
 			if (p_cell->uas.status<300) {
619
+				/* For e2e ACKs, From's tag 'MUST' equal INVITE's, while use
620
+				 * of the URI in this case is to be deprecated (Sec. 12.2.1.1).
621
+				 * Comparing entire From body is dangerous, since some UAs
622
+				 * screw the display name up. */
623
+				if (parse_from_header(p_msg) < 0) {
624
+					ERR("failed to parse From HF; ACK might not match.\n");
625
+					continue;
626
+				}
627
+				if (! STR_EQ(get_from(t_msg)->tag_value, 
628
+						get_from(p_msg)->tag_value))
629
+					continue;
630
+#ifdef TM_E2E_ACK_CHECK_FROM_URI
631
+				if (! STR_EQ(get_from(t_msg)->uri, 
632
+						get_from(p_msg)->uri))
633
+					continue;
634
+#endif
635
+
621 636
 				/* all criteria for proxied ACK are ok */
622 637
 				if (likely(p_cell->relayed_reply_branch!=-2)) {
623 638
 					if (unlikely(has_tran_tmcbs(p_cell, 
... ...
@@ -633,6 +648,10 @@ int t_lookup_request( struct sip_msg* p_msg , int leave_new_locked,
633 648
 				if (dlg_matching(p_cell, p_msg))
634 649
 					goto found;
635 650
 				continue;
651
+			} else {
652
+				/* for hbh ACKs, From HF 'MUST' equal INVITE's one */
653
+				if (! EQ_LEN(from)) continue;
654
+				if (! EQ_STR(from)) continue;
636 655
 			}
637 656
 			
638 657
 			/* it is not an e2e ACK/200 -- perhaps it is