Browse code

Merge commit 'origin/andrei/path'

* commit 'origin/andrei/path':
core: add path route headers after local via
core: path support when forwarding
tm: path support
xlog(s): updated to the new next_branch()
registrar(s): updated to the new append_branch()
permissions(s): updated to the new next_branch()
osp(s): updated to the new append_branch()
exec(s): use ser_append_branch() instead of append_branch()
cpl-c(s): updated to the new append_branch()
tm: updated to the new append_branch() & next_branch()
enum: s/km_append_brach/append_branch/
avpops: updated to the new append_branch()
core: append_branch & next_branch api changes

Conflicts:
modules/tm/sip_msg.c
modules/tm/t_fwd.c

Andrei Pelinescu-Onciul authored on 18/09/2009 11:36:33
Showing 20 changed files
... ...
@@ -345,7 +345,7 @@ int do_action(struct run_act_ctx* h, struct action* a, struct sip_msg* msg)
345 345
 				ret=E_BUG;
346 346
 				goto error;
347 347
 			}
348
-			ret=append_branch( msg, a->val[0].u.string,
348
+			ret=ser_append_branch( msg, a->val[0].u.string,
349 349
 					   a->val[0].u.string ? strlen(a->val[0].u.string):0,
350 350
 					   0, 0, a->val[1].u.number, 0);
351 351
 			break;
... ...
@@ -160,41 +160,6 @@ int get_branch_iterator(void)
160 160
 	return branch_iterator;
161 161
 }
162 162
 
163
-/*
164
- * Return the next branch from the dset
165
- * array, 0 is returned if there are no
166
- * more branches
167
- */
168
-char* next_branch(int* len, qvalue_t* q, char** dst_uri, int* dst_len, struct socket_info** force_socket)
169
-{
170
-	unsigned int i;
171
-
172
-	i = branch_iterator;
173
-	if (i < nr_branches) {
174
-		branch_iterator++;
175
-		*len = branches[i].len;
176
-		*q = branches[i].q;
177
-		if (dst_uri && dst_len) {
178
-			*dst_uri = branches[i].dst_uri;
179
-			*dst_len = branches[i].dst_uri_len;
180
-		}
181
-		if (force_socket) {
182
-			*force_socket = branches[i].force_send_socket;
183
-		}
184
-		return branches[i].uri;
185
-	} else {
186
-		*len = 0;
187
-		*q = Q_UNSPECIFIED;
188
-		if (dst_uri && dst_len) {
189
-			*dst_uri = 0;
190
-			*dst_len = 0;
191
-		}
192
-		if (force_socket) {
193
-			*force_socket = 0;
194
-		}
195
-		return 0;
196
-	}
197
-}
198 163
 
199 164
 
200 165
 /** \brief Get a branch from the destination set
... ...
@@ -203,7 +168,8 @@ char* next_branch(int* len, qvalue_t* q, char** dst_uri, int* dst_len, struct so
203 168
  * more branches
204 169
  */
205 170
 char* get_branch(unsigned int i, int* len, qvalue_t* q, str* dst_uri,
206
-				 str* path, unsigned int *flags, struct socket_info** force_socket)
171
+				 str* path, unsigned int *flags,
172
+				 struct socket_info** force_socket)
207 173
 {
208 174
 	if (i < nr_branches) {
209 175
 		*len = branches[i].len;
... ...
@@ -228,6 +194,10 @@ char* get_branch(unsigned int i, int* len, qvalue_t* q, str* dst_uri,
228 194
 			dst_uri->s = 0;
229 195
 			dst_uri->len = 0;
230 196
 		}
197
+		if (path) {
198
+			path->s = 0;
199
+			path->len = 0;
200
+		}
231 201
 		if (force_socket)
232 202
 			*force_socket = 0;
233 203
 		if (flags)
... ...
@@ -237,6 +207,23 @@ char* get_branch(unsigned int i, int* len, qvalue_t* q, str* dst_uri,
237 207
 }
238 208
 
239 209
 
210
+
211
+/** Return the next branch from the dset array.
212
+ * 0 is returned if there are no more branches
213
+ */
214
+char* next_branch(int* len, qvalue_t* q, str* dst_uri, str* path,
215
+					unsigned int* flags, struct socket_info** force_socket)
216
+{
217
+	char* ret;
218
+	
219
+	ret=get_branch(branch_iterator, len, q, dst_uri, path, flags,
220
+					force_socket);
221
+	if (likely(ret))
222
+		branch_iterator++;
223
+	return ret;
224
+}
225
+
226
+
240 227
 /*
241 228
  * Empty the dset array
242 229
  */
... ...
@@ -247,84 +234,32 @@ void clear_branches(void)
247 234
 }
248 235
 
249 236
 
250
-/* 
251
- * Add a new branch to current transaction 
252
- */
253
-int append_branch(struct sip_msg* msg, char* uri, int uri_len, char* dst_uri, int dst_uri_len, 
254
-		  qvalue_t q, struct socket_info* force_socket)
255
-{
256
-	     /* if we have already set up the maximum number
257
-	      * of branches, don't try new ones 
258
-	      */
259
-	if (nr_branches == MAX_BRANCHES - 1) {
260
-		LOG(L_ERR, "ERROR: append_branch: max nr of branches exceeded\n");
261
-		ser_error = E_TOO_MANY_BRANCHES;
262
-		return -1;
263
-	}
264
-
265
-	if (uri_len > MAX_URI_SIZE - 1) {
266
-		LOG(L_ERR, "ERROR: append_branch: too long uri: %.*s\n",
267
-		    uri_len, uri);
268
-		return -1;
269
-	}
270
-	
271
-	if (dst_uri_len > MAX_URI_SIZE - 1) {
272
-		LOG(L_ERR, "ERROR: append_branch: too long dst_uri: %.*s\n",
273
-		    dst_uri_len, ZSW(dst_uri));
274
-		return -1;
275
-	}
276
-
277
-	     /* if not parameterized, take current uri */
278
-	if (uri == 0) {
279
-		if (msg->new_uri.s) { 
280
-			uri = msg->new_uri.s;
281
-			uri_len = msg->new_uri.len;
282
-		} else {
283
-			uri = msg->first_line.u.request.uri.s;
284
-			uri_len = msg->first_line.u.request.uri.len;
285
-		}
286
-	}
287
-	
288
-	memcpy(branches[nr_branches].uri, uri, uri_len);
289
-	     /* be safe -- add zero termination */
290
-	branches[nr_branches].uri[uri_len] = 0;
291
-	branches[nr_branches].len = uri_len;
292
-	branches[nr_branches].q = q;
293
-	
294
- 	if (dst_uri && dst_uri_len) {
295
-  		memcpy(branches[nr_branches].dst_uri, dst_uri, dst_uri_len);
296
-  		branches[nr_branches].dst_uri[dst_uri_len] = 0;
297
-  		branches[nr_branches].dst_uri_len = dst_uri_len;
298
- 	} else {
299
- 		branches[nr_branches].dst_uri[0] = '\0';
300
- 		branches[nr_branches].dst_uri_len = 0;
301
-	}
302
-
303
-	branches[nr_branches].force_send_socket = force_socket;
304
-	
305
-	nr_branches++;
306
-	return 1;
307
-}
308
-
309 237
 
310
-/* ! \brief
311
- * Add a new branch to current transaction using str parameters
312
- * Kamailio compatibility version
238
+/**  Add a new branch to the current transaction.
239
+ * @param msg - sip message, used for getting the uri if not specified (0).
240
+ * @param uri - uri, can be 0 (in which case the uri is taken from msg)
241
+ * @param dst_uri - destination uri, can be 0.
242
+ * @param path - path vector (passed in a string), can be 0.
243
+ * @param q  - q value.
244
+ * @param flags - per branch flags.
245
+ * @param force_socket - socket that should be used when sending.
246
+ *
247
+ * @return  <0 (-1) on failure, 1 on success (script convention).
313 248
  */
314
-int km_append_branch(struct sip_msg* msg, str* uri, str* dst_uri, str* path,
249
+int append_branch(struct sip_msg* msg, str* uri, str* dst_uri, str* path,
315 250
 		qvalue_t q, unsigned int flags, struct socket_info* force_socket)
316 251
 {
317 252
 	str luri;
318 253
 
319 254
 #ifdef USE_LOCAL_ROUTE
320
-	if (dset_state==0)
255
+	if (unlikely(dset_state==0))
321 256
 		return -1;
322 257
 #endif
323 258
 
324 259
 	/* if we have already set up the maximum number
325 260
 	 * of branches, don't try new ones 
326 261
 	 */
327
-	if (nr_branches == MAX_BRANCHES - 1) {
262
+	if (unlikely(nr_branches == MAX_BRANCHES - 1)) {
328 263
 		LOG(L_ERR, "max nr of branches exceeded\n");
329 264
 		ser_error = E_TOO_MANY_BRANCHES;
330 265
 		return -1;
... ...
@@ -340,16 +275,15 @@ int km_append_branch(struct sip_msg* msg, str* uri, str* dst_uri, str* path,
340 275
 		luri = *uri;
341 276
 	}
342 277
 
343
-	if (luri.len > MAX_URI_SIZE - 1) {
278
+	if (unlikely(luri.len > MAX_URI_SIZE - 1)) {
344 279
 		LOG(L_ERR, "too long uri: %.*s\n", luri.len, luri.s);
345 280
 		return -1;
346 281
 	}
347 282
 
348 283
 	/* copy the dst_uri */
349 284
 	if (dst_uri && dst_uri->len && dst_uri->s) {
350
-		if (dst_uri->len > MAX_URI_SIZE - 1) {
351
-			LOG(L_ERR, "too long dst_uri: %.*s\n",
352
-				dst_uri->len, dst_uri->s);
285
+		if (unlikely(dst_uri->len > MAX_URI_SIZE - 1)) {
286
+			LOG(L_ERR, "too long dst_uri: %.*s\n", dst_uri->len, dst_uri->s);
353 287
 			return -1;
354 288
 		}
355 289
 		memcpy(branches[nr_branches].dst_uri, dst_uri->s, dst_uri->len);
... ...
@@ -361,8 +295,8 @@ int km_append_branch(struct sip_msg* msg, str* uri, str* dst_uri, str* path,
361 295
 	}
362 296
 
363 297
 	/* copy the path string */
364
-	if (path && path->len && path->s) {
365
-		if (path->len > MAX_PATH_SIZE - 1) {
298
+	if (unlikely(path && path->len && path->s)) {
299
+		if (unlikely(path->len > MAX_PATH_SIZE - 1)) {
366 300
 			LOG(L_ERR, "too long path: %.*s\n", path->len, path->s);
367 301
 			return -1;
368 302
 		}
... ...
@@ -413,7 +347,7 @@ char* print_dset(struct sip_msg* msg, int* len)
413 347
 	}
414 348
 
415 349
 	init_branch_iterator();
416
-	while ((uri.s = next_branch(&uri.len, &q, 0, 0, 0))) {
350
+	while ((uri.s = next_branch(&uri.len, &q, 0, 0, 0, 0))) {
417 351
 		cnt++;
418 352
 		*len += uri.len;
419 353
 		if (q != Q_UNSPECIFIED) {
... ...
@@ -454,7 +388,7 @@ char* print_dset(struct sip_msg* msg, int* len)
454 388
 	}
455 389
 
456 390
 	init_branch_iterator();
457
-	while ((uri.s = next_branch(&uri.len, &q, 0, 0, 0))) {
391
+	while ((uri.s = next_branch(&uri.len, &q, 0, 0, 0, 0))) {
458 392
 		if (i) {
459 393
 			memcpy(p, CONTACT_DELIM, CONTACT_DELIM_LEN);
460 394
 			p += CONTACT_DELIM_LEN;
... ...
@@ -37,18 +37,39 @@ struct sip_msg;
37 37
 extern unsigned int nr_branches;
38 38
 
39 39
 
40
-/* 
40
+
41
+/*
41 42
  * Add a new branch to current transaction 
42 43
  */
43
-int append_branch(struct sip_msg* msg, char* uri, int uri_len, char* dst_uri, int dst_uri_len, 
44
-		  qvalue_t q, struct socket_info* force_socket);
44
+int append_branch(struct sip_msg* msg, str* uri, str* dst_uri, str* path,
45
+					 qvalue_t q, unsigned int flags,
46
+					 struct socket_info* force_socket);
45 47
 
48
+/* kamailio compatible version */
49
+#define km_append_branch(msg, uri, dst_uri, path, q, flags, force_socket) \
50
+	append_branch(msg, uri, dst_uri, path, q, flags, force_socket)
46 51
 
47
-int km_append_branch(struct sip_msg* msg, str* uri, str* dst_uri, str* path,
48
-					 qvalue_t q, unsigned int flags, struct socket_info* force_socket);
52
+/** ser compatible append_branch version.
53
+ *  append_branch version compatible with ser: no path or branch flags support
54
+ *  and no str parameters.
55
+ */
56
+static inline int ser_append_branch(struct sip_msg* msg,
57
+									char* uri, int uri_len,
58
+									char* dst_uri, int dst_uri_len,
59
+									qvalue_t q,
60
+									struct socket_info* force_socket)
61
+{
62
+	str s_uri, s_dst_uri;
63
+	s_uri.s=uri;
64
+	s_uri.len=uri_len;
65
+	s_dst_uri.s=dst_uri;
66
+	s_dst_uri.len=dst_uri_len;
67
+	return append_branch(msg, &s_uri, &s_dst_uri, 0, q, 0, force_socket);
68
+}
49 69
 
50 70
 
51
-/* 
71
+
72
+/*
52 73
  * Iterate through the list of transaction branches 
53 74
  */
54 75
 void init_branch_iterator(void);
... ...
@@ -58,14 +79,19 @@ void init_branch_iterator(void);
58 79
  */
59 80
 int get_branch_iterator(void);
60 81
 
61
-/*
62
- * Get the next branch in the current transaction
82
+
83
+/** Get the next branch in the current transaction.
84
+ * @return pointer to the uri of the next branch (which the length written in
85
+ *  *len) or 0 if there are no more branches.
63 86
  */
64
-char* next_branch(int* len, qvalue_t* q, char** dst_uri, int* dst_len, struct socket_info** force_socket);
87
+char* next_branch(int* len, qvalue_t* q, str* dst_uri, str* path,
88
+					unsigned int* flags, struct socket_info** force_socket);
65 89
 
66 90
 
67 91
 char* get_branch( unsigned int i, int* len, qvalue_t* q, str* dst_uri,
68
-				  str* path, unsigned int *flags, struct socket_info** force_socket);
92
+				  str* path, unsigned int *flags,
93
+				  struct socket_info** force_socket);
94
+
69 95
 
70 96
 
71 97
 /*
... ...
@@ -998,7 +998,7 @@ int ops_pushto_avp (struct sip_msg* msg, struct fis_param* dst,
998 998
 			{
999 999
 				/* if is not the first modification, push the current uri as
1000 1000
 				 * branch */
1001
-				if (append_branch( msg, 0, 0, 0, 0, Q_UNSPECIFIED, 0)!=1 )
1001
+				if (append_branch( msg, 0, 0, 0, Q_UNSPECIFIED, 0, 0)!=1 )
1002 1002
 				{
1003 1003
 					LM_ERR("append_branch action failed\n");
1004 1004
 					goto error;
... ...
@@ -1021,8 +1021,8 @@ int ops_pushto_avp (struct sip_msg* msg, struct fis_param* dst,
1021 1021
 				goto error;
1022 1022
 			}
1023 1023
 		} else if (dst->opd&AVPOPS_USE_BRANCH) {
1024
-			if (append_branch( msg, val.s, val.len, 0, 0, Q_UNSPECIFIED,
1025
-			msg->force_send_socket)!=1 )
1024
+			if (append_branch( msg, &val, 0, 0, Q_UNSPECIFIED, 0,
1025
+								msg->force_send_socket)!=1 )
1026 1026
 			{
1027 1027
 				LM_ERR("append_branch action failed\n");
1028 1028
 				goto error;
... ...
@@ -662,7 +662,7 @@ int do_query(struct sip_msg* _msg, char *user, char *name, str *service) {
662 662
 		q = q - 10;
663 663
 		curr_prio = priority;
664 664
 	    }
665
-	    if (km_append_branch(_msg, &result, 0, 0, q, 0, 0) == -1) {
665
+	    if (append_branch(_msg, &result, 0, 0, q, 0, 0) == -1) {
666 666
 		goto done;
667 667
 	    }
668 668
 	}
... ...
@@ -1105,7 +1105,7 @@ int enum_pv_query_3(struct sip_msg* _msg, char* _sp, char* _suffix,
1105 1105
 				q = q - 10;
1106 1106
 				curr_prio = priority;
1107 1107
 			}
1108
-			if (km_append_branch(_msg, &result, 0, 0, q, 0, 0) == -1) {
1108
+			if (append_branch(_msg, &result, 0, 0, q, 0, 0) == -1) {
1109 1109
 				goto done;
1110 1110
 			}
1111 1111
 		}
... ...
@@ -182,6 +182,9 @@ void free_cell( struct cell* dead_cell )
182 182
 		}
183 183
 		dns_srv_handle_put_shm_unsafe(&dead_cell->uac[i].dns_h);
184 184
 #endif
185
+		if (unlikely(dead_cell->uac[i].path.s)) {
186
+			shm_free_unsafe(dead_cell->uac[i].path.s);
187
+		}
185 188
 	}
186 189
 
187 190
 #ifdef WITH_AS_SUPPORT
... ...
@@ -219,7 +219,8 @@ typedef struct ua_client
219 219
 #ifdef USE_DNS_FAILOVER
220 220
 	struct dns_srv_handle dns_h;
221 221
 #endif
222
-	str              uri;
222
+	str uri;
223
+	str path;
223 224
 	/* if we don't store, we at least want to know the status */
224 225
 	int             last_received;
225 226
 
... ...
@@ -145,7 +145,7 @@ unsigned int get_on_branch(void)
145 145
 
146 146
 
147 147
 static char *print_uac_request( struct cell *t, struct sip_msg *i_req,
148
-	int branch, str *uri, unsigned int *len, struct dest_info* dst)
148
+	int branch, str *uri, str* path, unsigned int *len, struct dest_info* dst)
149 149
 {
150 150
 	char *buf, *shbuf;
151 151
 	str* msg_uri;
... ...
@@ -153,6 +153,8 @@ static char *print_uac_request( struct cell *t, struct sip_msg *i_req,
153 153
 	struct sip_uri parsed_uri_bak;
154 154
 	int parsed_uri_ok_bak, uri_backed_up;
155 155
 	str msg_uri_bak;
156
+	str path_bak;
157
+	int path_backed_up;
156 158
 	int backup_route_type;
157 159
 
158 160
 	shbuf=0;
... ...
@@ -160,6 +162,9 @@ static char *print_uac_request( struct cell *t, struct sip_msg *i_req,
160 162
 	msg_uri_bak.len=0;
161 163
 	parsed_uri_ok_bak=0;
162 164
 	uri_backed_up=0;
165
+	path_bak.s=0;
166
+	path_bak.len=0;
167
+	path_backed_up=0;
163 168
 
164 169
 	/* ... we calculate branch ... */	
165 170
 	if (!t_calc_branch(t, branch, i_req->add_to_branch_s,
... ...
@@ -179,6 +184,13 @@ static char *print_uac_request( struct cell *t, struct sip_msg *i_req,
179 184
 		i_req->parsed_uri_ok=0;
180 185
 		uri_backed_up=1;
181 186
 	}
187
+	/* update path_vec */
188
+	if (unlikely((i_req->path_vec.s!=path->s) ||
189
+					(i_req->path_vec.len!=path->len))){
190
+		path_bak=i_req->path_vec;
191
+		i_req->path_vec=*path;
192
+		path_backed_up=1;
193
+	}
182 194
 
183 195
 #ifdef POSTPONE_MSG_CLONING
184 196
 	/* lumps can be set outside of the lock, make sure that we read
... ...
@@ -191,13 +203,13 @@ static char *print_uac_request( struct cell *t, struct sip_msg *i_req,
191 203
 	i_req->body_lumps = dup_lump_list(i_req->body_lumps);
192 204
 
193 205
 	if (unlikely(branch_route)) {
194
-		     /* run branch_route actions if provided */
206
+		/* run branch_route actions if provided */
195 207
 		backup_route_type = get_route_type();
196 208
 		set_route_type(BRANCH_ROUTE);
197 209
 		tm_ctx_set_branch_index(branch+1);
198 210
 		if (exec_pre_script_cb(i_req, BRANCH_CB_TYPE)>0) {
199 211
 			if (run_top_route(branch_rt.rlist[branch_route], i_req, 0) < 0) {
200
-				LOG(L_ERR, "ERROR: print_uac_request: Error in run_top_route\n");
212
+				LOG(L_ERR, "Error in run_top_route\n");
201 213
 			}
202 214
 			exec_post_script_cb(i_req, BRANCH_CB_TYPE);
203 215
 		}		
... ...
@@ -251,17 +263,22 @@ error01:
251 263
 		i_req->parsed_uri=parsed_uri_bak;
252 264
 		i_req->parsed_uri_ok=parsed_uri_ok_bak;
253 265
 	}
266
+	if (unlikely(path_backed_up)){
267
+		i_req->path_vec=path_bak;
268
+	}
254 269
 
255
- error00:
270
+error00:
256 271
 	return shbuf;
257 272
 }
258 273
 
259 274
 #ifdef USE_DNS_FAILOVER
260
-/* Similar to print_uac_request(), but this function uses the outgoing message buffer of
261
-   the failed branch to construt the new message in case of DNS failover.
275
+/* Similar to print_uac_request(), but this function uses the outgoing message
276
+   buffer of the failed branch to construct the new message in case of DNS 
277
+   failover.
262 278
 
263 279
    WARNING: only the first VIA header is replaced in the buffer, the rest
264
-   of the message is untuched, thus, the send socket is corrected only in the VIA HF.
280
+   of the message is untouched, thus, the send socket is corrected only in the
281
+   VIA HF.
265 282
 */
266 283
 static char *print_uac_request_from_buf( struct cell *t, struct sip_msg *i_req,
267 284
 	int branch, str *uri, unsigned int *len, struct dest_info* dst,
... ...
@@ -381,7 +398,7 @@ int add_blind_uac( /*struct cell *t*/ )
381 398
    On error returns <0 & sets ser_error to the same value
382 399
 */
383 400
 int add_uac( struct cell *t, struct sip_msg *request, str *uri, str* next_hop,
384
-	struct proxy_l *proxy, int proto )
401
+				str* path, struct proxy_l *proxy, int proto )
385 402
 {
386 403
 
387 404
 	int ret;
... ...
@@ -441,7 +458,7 @@ int add_uac( struct cell *t, struct sip_msg *request, str *uri, str* next_hop,
441 458
 	}
442 459
 
443 460
 	/* now message printing starts ... */
444
-	shbuf=print_uac_request( t, request, branch, uri, 
461
+	shbuf=print_uac_request(t, request, branch, uri, path,
445 462
 							&len, &t->uac[branch].request.dst);
446 463
 	if (!shbuf) {
447 464
 		ret=ser_error=E_OUT_OF_MEM;
... ...
@@ -454,6 +471,21 @@ int add_uac( struct cell *t, struct sip_msg *request, str *uri, str* next_hop,
454 471
 	t->uac[branch].uri.s=t->uac[branch].request.buffer+
455 472
 		request->first_line.u.request.method.len+1;
456 473
 	t->uac[branch].uri.len=uri->len;
474
+	if (unlikely(path && path->s)){
475
+		t->uac[branch].path.s=shm_malloc(path->len+1);
476
+		if (unlikely(t->uac[branch].path.s==0)) {
477
+			shm_free(shbuf);
478
+			t->uac[branch].request.buffer=0;
479
+			t->uac[branch].request.buffer_len=0;
480
+			t->uac[branch].uri.s=0;
481
+			t->uac[branch].uri.len=0;
482
+			ret=ser_error=E_OUT_OF_MEM;
483
+			goto error01;
484
+		}
485
+		t->uac[branch].path.len=path->len;
486
+		t->uac[branch].path.s[path->len]=0;
487
+		memcpy( t->uac[branch].path.s, path->s, path->len);
488
+	}
457 489
 #ifdef TM_UAC_FLAGS
458 490
 	len = count_applied_lumps(request->add_rm, HDR_RECORDROUTE_T);
459 491
 	if(len==1)
... ...
@@ -483,10 +515,11 @@ error:
483 515
 
484 516
 #ifdef USE_DNS_FAILOVER
485 517
 /* Similar to add_uac(), but this function uses the outgoing message buffer of
486
-   the failed branch to construt the new message in case of DNS failover.
518
+   the failed branch to construct the new message in case of DNS failover.
487 519
 */
488
-static int add_uac_from_buf( struct cell *t, struct sip_msg *request, str *uri, int proto,
489
-			char *buf, short buf_len)
520
+static int add_uac_from_buf( struct cell *t, struct sip_msg *request,
521
+								str *uri, str* path, int proto,
522
+								char *buf, short buf_len)
490 523
 {
491 524
 
492 525
 	int ret;
... ...
@@ -496,7 +529,8 @@ static int add_uac_from_buf( struct cell *t, struct sip_msg *request, str *uri,
496 529
 
497 530
 	branch=t->nr_of_outgoings;
498 531
 	if (branch==MAX_BRANCHES) {
499
-		LOG(L_ERR, "ERROR: add_uac_from_buf: maximum number of branches exceeded\n");
532
+		LOG(L_ERR, "ERROR: add_uac_from_buf: maximum number of branches"
533
+					" exceeded\n");
500 534
 		ret=ser_error=E_TOO_MANY_BRANCHES;
501 535
 		goto error;
502 536
 	}
... ...
@@ -526,7 +560,7 @@ static int add_uac_from_buf( struct cell *t, struct sip_msg *request, str *uri,
526 560
 	}
527 561
 
528 562
 	/* now message printing starts ... */
529
-	shbuf=print_uac_request_from_buf( t, request, branch, uri, 
563
+	shbuf=print_uac_request_from_buf( t, request, branch, uri,
530 564
 							&len, &t->uac[branch].request.dst,
531 565
 							buf, buf_len);
532 566
 	if (!shbuf) {
... ...
@@ -540,6 +574,22 @@ static int add_uac_from_buf( struct cell *t, struct sip_msg *request, str *uri,
540 574
 	t->uac[branch].uri.s=t->uac[branch].request.buffer+
541 575
 		request->first_line.u.request.method.len+1;
542 576
 	t->uac[branch].uri.len=uri->len;
577
+	/* copy the path */
578
+	if (unlikely(path && path->s)){
579
+		t->uac[branch].path.s=shm_malloc(path->len+1);
580
+		if (unlikely(t->uac[branch].path.s==0)) {
581
+			shm_free(shbuf);
582
+			t->uac[branch].request.buffer=0;
583
+			t->uac[branch].request.buffer_len=0;
584
+			t->uac[branch].uri.s=0;
585
+			t->uac[branch].uri.len=0;
586
+			ret=ser_error=E_OUT_OF_MEM;
587
+			goto error;
588
+		}
589
+		t->uac[branch].path.len=path->len;
590
+		t->uac[branch].path.s[path->len]=0;
591
+		memcpy( t->uac[branch].path.s, path->s, path->len);
592
+	}
543 593
 	membar_write(); /* to allow lockless ops (e.g. prepare_to_cancel()) we want
544 594
 					   to be sure everything above is fully written before
545 595
 					   updating branches no. */
... ...
@@ -564,7 +614,7 @@ error:
564 614
    already held, e.g. in failure route/handlers (WARNING: using 1 in a 
565 615
    failure route will cause a deadlock).
566 616
 */
567
-int add_uac_dns_fallback( struct cell *t, struct sip_msg* msg, 
617
+int add_uac_dns_fallback(struct cell *t, struct sip_msg* msg,
568 618
 									struct ua_client* old_uac,
569 619
 									int lock_replies)
570 620
 {
... ...
@@ -600,9 +650,10 @@ int add_uac_dns_fallback( struct cell *t, struct sip_msg* msg,
600 650
 
601 651
 			if (cfg_get(tm, tm_cfg, reparse_on_dns_failover))
602 652
 				/* Reuse the old buffer and only replace the via header.
603
-				 * The drowback is that the send_socket is not corrected
653
+				 * The drawback is that the send_socket is not corrected
604 654
 				 * in the rest of the message, only in the VIA HF (Miklos) */
605
-				ret=add_uac_from_buf(t,  msg, &old_uac->uri, 
655
+				ret=add_uac_from_buf(t,  msg, &old_uac->uri,
656
+							&old_uac->path,
606 657
 							old_uac->request.dst.proto,
607 658
 							old_uac->request.buffer,
608 659
 							old_uac->request.buffer_len);
... ...
@@ -611,7 +662,7 @@ int add_uac_dns_fallback( struct cell *t, struct sip_msg* msg,
611 662
 				 * Unfortunately we can't reuse the old buffer, the branch id
612 663
 				 *  must be changed and the send_socket might be different =>
613 664
 				 *  re-create the whole uac */
614
-				ret=add_uac(t,  msg, &old_uac->uri, 0, 0, 
665
+				ret=add_uac(t,  msg, &old_uac->uri, 0, &old_uac->path, 0,
615 666
 							old_uac->request.dst.proto);
616 667
 
617 668
 			if (ret<0){
... ...
@@ -666,9 +717,10 @@ int e2e_cancel_branch( struct sip_msg *cancel_msg, struct cell *t_cancel,
666 717
 
667 718
 	} else {
668 719
 		/* buffer is constructed from the received CANCEL with applying lumps */
669
-		shbuf=print_uac_request( t_cancel, cancel_msg, branch, 
670
-							&t_invite->uac[branch].uri, &len, 
671
-							&t_invite->uac[branch].request.dst);
720
+		shbuf=print_uac_request( t_cancel, cancel_msg, branch,
721
+							&t_invite->uac[branch].uri,
722
+							&t_invite->uac[branch].path,
723
+							&len, &t_invite->uac[branch].request.dst);
672 724
 	}
673 725
 
674 726
 	if (!shbuf) {
... ...
@@ -1015,7 +1067,7 @@ int t_forward_nonack( struct cell *t, struct sip_msg* p_msg ,
1015 1067
 	int success_branch;
1016 1068
 	int try_new;
1017 1069
 	int lock_replies;
1018
-	str dst_uri;
1070
+	str dst_uri, path;
1019 1071
 	struct socket_info* si, *backup_si;
1020 1072
 	flag_t backup_bflags = 0;
1021 1073
 	flag_t bflags = 0;
... ...
@@ -1077,7 +1129,7 @@ int t_forward_nonack( struct cell *t, struct sip_msg* p_msg ,
1077 1129
 #endif
1078 1130
 		try_new=1;
1079 1131
 		branch_ret=add_uac( t, p_msg, GET_RURI(p_msg), GET_NEXT_HOP(p_msg),
1080
-							proxy, proto );
1132
+							&p_msg->path_vec, proxy, proto );
1081 1133
 		if (branch_ret>=0) 
1082 1134
 			added_branches |= 1<<branch_ret;
1083 1135
 		else
... ...
@@ -1085,16 +1137,15 @@ int t_forward_nonack( struct cell *t, struct sip_msg* p_msg ,
1085 1137
 	} else try_new=0;
1086 1138
 
1087 1139
 	init_branch_iterator();
1088
-	while((current_uri.s=next_branch( &current_uri.len, &q, &dst_uri.s,
1089
-										&dst_uri.len, &si))) {
1140
+	while((current_uri.s=next_branch( &current_uri.len, &q, &dst_uri, &path,
1141
+										&bflags, &si))) {
1090 1142
 		try_new++;
1091 1143
 		p_msg->force_send_socket = si;
1092
-		getbflagsval(get_branch_iterator(), &bflags);
1093 1144
 		setbflagsval(0, bflags);
1094 1145
 
1095
-		branch_ret=add_uac( t, p_msg, &current_uri, 
1096
-							(dst_uri.len) ? (&dst_uri) : &current_uri, 
1097
-							proxy, proto);
1146
+		branch_ret=add_uac( t, p_msg, &current_uri,
1147
+							(dst_uri.len) ? (&dst_uri) : &current_uri,
1148
+							&path, proxy, proto);
1098 1149
 		/* pick some of the errors in case things go wrong;
1099 1150
 		   note that picking lowest error is just as good as
1100 1151
 		   any other algorithm which picks any other negative
... ...
@@ -59,8 +59,8 @@ char *print_uac_request( struct cell *t, struct sip_msg *i_req,
59 59
 */
60 60
 void e2e_cancel( struct sip_msg *cancel_msg, struct cell *t_cancel, struct cell *t_invite );
61 61
 int e2e_cancel_branch( struct sip_msg *cancel_msg, struct cell *t_cancel, struct cell *t_invite, int branch );
62
-int add_uac(	struct cell *t, struct sip_msg *request, str *uri, str* next_hop,
63
-				struct proxy_l *proxy, int proto );
62
+int add_uac(struct cell *t, struct sip_msg *request, str *uri, str* next_hop,
63
+				str* path, struct proxy_l *proxy, int proto );
64 64
 #ifdef USE_DNS_FAILOVER
65 65
 int add_uac_dns_fallback( struct cell *t, struct sip_msg* msg, 
66 66
 									struct ua_client* old_uac,
... ...
@@ -448,7 +448,7 @@ int t_next_contacts(struct sip_msg* msg, char* key, char* value)
448 448
 				return -1;
449 449
 			}
450 450
 
451
-			if (km_append_branch(msg, &uri, &dst, &path, 0, flags, sock) != 1) {
451
+			if (append_branch(msg, &uri, &dst, &path, 0, flags, sock) != 1) {
452 452
 				LM_ERR("appending branch failed\n");
453 453
 				destroy_avp(avp);
454 454
 				return -1;
... ...
@@ -488,8 +488,8 @@ int t_next_contacts(struct sip_msg* msg, char* key, char* value)
488 488
 				destroy_avp(avp);
489 489
 				return -1;
490 490
 			}
491
-	    
492
-			if (km_append_branch(msg, &uri, &dst, &path, 0, flags, sock) != 1) {
491
+	
492
+			if (append_branch(msg, &uri, &dst, &path, 0, flags, sock) != 1) {
493 493
 				LM_ERR("appending branch failed\n");
494 494
 				destroy_avp(avp);
495 495
 				return -1;
... ...
@@ -83,7 +83,8 @@ int cpl_proxy_to_loc_set( struct sip_msg *msg, struct location **locs,
83 83
 	while(*locs) {
84 84
 		DBG("DEBUG:cpl_c:cpl_proxy_to_loc_set: appending branch "
85 85
 			"<%.*s>\n",(*locs)->addr.uri.len,(*locs)->addr.uri.s);
86
-		if(append_branch(msg,(*locs)->addr.uri.s,(*locs)->addr.uri.len,0, 0, Q_UNSPECIFIED, 0)==-1){
86
+		if(append_branch(msg, &(*locs)->addr.uri,
87
+							0, 0, Q_UNSPECIFIED, 0,  0)==-1){
87 88
 			LOG(L_ERR,"ERROR:cpl_c:cpl_proxy_to_loc_set: failed when "
88 89
 				"appending branch <%s>\n",(*locs)->addr.uri.s);
89 90
 			goto error;
... ...
@@ -171,7 +171,8 @@ int exec_str(struct sip_msg *msg, str* cmd, char *param, int param_len) {
171 171
 				goto error02;
172 172
 			}
173 173
 		} else {
174
-			if (append_branch(msg, uri_line, uri_len, 0, 0, Q_UNSPECIFIED, 0)==-1) {
174
+			if (ser_append_branch(msg, uri_line, uri_len, 0, 0,
175
+									Q_UNSPECIFIED, 0)==-1) {
175 176
 				LOG(L_ERR, "ERROR: exec_str: append_branch failed;"
176 177
 					" too many or too long URIs?\n");
177 178
 				goto error02;
... ...
@@ -452,7 +452,8 @@ static int ospPrepareDestination(
452 452
             if (isfirst == OSP_FIRST_ROUTE) {
453 453
                 rewrite_uri(msg, &newuri);
454 454
             } else {
455
-                append_branch(msg, newuri.s, newuri.len, NULL, 0, Q_UNSPECIFIED, NULL);
455
+                append_branch(msg, &newuri, NULL, NULL, Q_UNSPECIFIED,
456
+                              0, NULL);
456 457
             }
457 458
 
458 459
             result = MODULE_RETURNCODE_TRUE;
... ...
@@ -351,7 +351,7 @@ int check_routing(struct sip_msg* msg, int idx)
351 351
 
352 352
  check_branches:
353 353
         init_branch_iterator();
354
-        while((branch.s = next_branch(&branch.len, &q, 0, 0, 0))) {
354
+        while((branch.s = next_branch(&branch.len, &q, 0, 0, 0, 0))) {
355 355
                 uri_str = get_plain_uri(&branch);
356 356
                 if (!uri_str) {
357 357
                         LOG(L_ERR, "check_uri(): Error while extracting plain URI\n");
... ...
@@ -164,7 +164,7 @@ skip_rewrite_uri:
164 164
 					LOG(L_ERR, "ERROR: lookup(): branch: out of memory\n");
165 165
 					goto cont; /* try to continue */
166 166
 				}
167
-				if (append_branch(_m, new_uri.s, new_uri.len, 0, 0, ptr->q, 0) == -1) {
167
+				if (append_branch(_m, &new_uri, 0, 0, ptr->q, 0, 0) == -1) {
168 168
 					LOG(L_ERR, "lookup(): Error while appending a branch\n");
169 169
 					pkg_free(new_uri.s);
170 170
 					if (ser_error==E_TOO_MANY_BRANCHES) goto skip;
... ...
@@ -173,8 +173,8 @@ skip_rewrite_uri:
173 173
 				}
174 174
 				pkg_free(new_uri.s); /* append_branch doesn't free it */
175 175
 			}else{
176
-				if (append_branch(_m, ptr->c.s, ptr->c.len, ptr->received.s,
177
-							ptr->received.len, ptr->q, ptr->sock) == -1) {
176
+				if (append_branch(_m, &ptr->c, &ptr->received, 0 /* path */,
177
+									ptr->q, 0 /* brflags*/, ptr->sock) == -1) {
178 178
 					LOG(L_ERR, "lookup(): Error while appending a branch\n");
179 179
 					goto skip; /* Return OK here so the function succeeds */
180 180
 				}
... ...
@@ -326,7 +326,7 @@ skip_rewrite_uri:
326 326
 					ERR("branch: out of memory\n");
327 327
 					goto cont; /* try to continue */
328 328
 				}
329
-				if (append_branch(msg, new_uri.s, new_uri.len, 0, 0, ptr->q, 0) == -1) {
329
+				if (append_branch(msg, &new_uri, 0, 0, ptr->q, 0, 0) == -1) {
330 330
 					ERR("Error while appending a branch\n");
331 331
 					pkg_free(new_uri.s);
332 332
 					if (ser_error == E_TOO_MANY_BRANCHES) goto skip;
... ...
@@ -335,8 +335,8 @@ skip_rewrite_uri:
335 335
 				}
336 336
 				pkg_free(new_uri.s); /* append_branch doesn't free it */
337 337
 			} else {
338
-				if (append_branch(msg, ptr->c.s, ptr->c.len, ptr->received.s,
339
-							ptr->received.len, ptr->q, ptr->sock) == -1) {
338
+				if (append_branch(msg, &ptr->c, &ptr->received, 0 /* path */,
339
+									 ptr->q, 0, ptr->sock) == -1) {
340 340
 					ERR("Error while appending a branch\n");
341 341
 					goto skip; /* Return OK here so the function succeeds */
342 342
 				}
... ...
@@ -699,7 +699,7 @@ static int xl_get_branch(struct sip_msg *msg, str *res, str *hp, int hi, int hf)
699 699
 
700 700
 
701 701
 	init_branch_iterator();
702
-	branch.s = next_branch(&branch.len, &q, 0, 0, 0);
702
+	branch.s = next_branch(&branch.len, &q, 0, 0, 0, 0);
703 703
 	if (!branch.s) {
704 704
 		return xl_get_null(msg, res, hp, hi, hf);
705 705
 	}
... ...
@@ -730,7 +730,7 @@ static int xl_get_branches(struct sip_msg *msg, str *res, str *hp, int hi, int h
730 730
 	cnt = len = 0;
731 731
 
732 732
 	init_branch_iterator();
733
-	while ((uri.s = next_branch(&uri.len, &q, 0, 0, 0)))
733
+	while ((uri.s = next_branch(&uri.len, &q, 0, 0, 0, 0)))
734 734
 	{
735 735
 		cnt++;
736 736
 		len += uri.len;
... ...
@@ -755,7 +755,7 @@ static int xl_get_branches(struct sip_msg *msg, str *res, str *hp, int hi, int h
755 755
 	p = local_buf;
756 756
 
757 757
 	init_branch_iterator();
758
-	while ((uri.s = next_branch(&uri.len, &q, 0, 0, 0)))
758
+	while ((uri.s = next_branch(&uri.len, &q, 0, 0, 0, 0)))
759 759
 	{
760 760
 		if (i)
761 761
 		{
... ...
@@ -1495,7 +1495,9 @@ error:
1495 1495
 /** builds a request in memory from another sip request.
1496 1496
   *
1497 1497
   * Side-effects: - it adds lumps to the msg which are _not_ cleaned.
1498
-  * All the added lumps are HDR_VIA_T.
1498
+  * The added lumps are HDR_VIA_T (almost always added), HDR_CONTENLENGTH_T
1499
+  * and HDR_ROUTE_T (when a Route: header is added as a result of a non-null
1500
+  * msg->path_vec).
1499 1501
   *               - it might change send_info->proto and send_info->send_socket
1500 1502
   *                 if proto fallback is enabled (see below).
1501 1503
   *
... ...
@@ -1516,8 +1518,16 @@ error:
1516 1518
   *                       message > mtu and send_info->proto==PROTO_UDP. 
1517 1519
   *                       It will also update send_info->proto.
1518 1520
   *                     - FL_FORCE_RPORT: add rport to via
1521
+  * @param mode - flags for building the message, can be a combination of:
1522
+  *                 * BUILD_NO_LOCAL_VIA - don't add a local via
1523
+  *                 * BUILD_NO_VIA1_UPDATE - don't update first via (rport,
1524
+  *                    received a.s.o)
1525
+  *                 * BUILD_NO_PATH - don't add a Route: header with the 
1526
+  *                   msg->path_vec content.
1527
+  *                 * BUILD_IN_SHM - build the result in shm memory
1519 1528
   *
1520
-  * @return pointer to the new request (pkg_malloc'ed, needs freeing when
1529
+  * @return pointer to the new request (pkg_malloc'ed or shm_malloc'ed,
1530
+  * depending on the presence of the BUILD_IN_SHM flag, needs freeing when
1521 1531
   *   done) and sets returned_len or 0 on error.
1522 1532
   */
1523 1533
 char * build_req_buf_from_sip_req( struct sip_msg* msg,
... ...
@@ -1532,10 +1542,13 @@ char * build_req_buf_from_sip_req( struct sip_msg* msg,
1532 1542
 	char* rport_buf;
1533 1543
 	char* new_buf;
1534 1544
 	char* buf;
1545
+	str path_buf;
1535 1546
 	unsigned int offset, s_offset, size;
1536 1547
 	struct lump* via_anchor;
1537 1548
 	struct lump* via_lump;
1538 1549
 	struct lump* via_insert_param;
1550
+	struct lump* path_anchor;
1551
+	struct lump* path_lump;
1539 1552
 	str branch;
1540 1553
 	unsigned int flags;
1541 1554
 	unsigned int udp_mtu;
... ...
@@ -1550,8 +1563,11 @@ char * build_req_buf_from_sip_req( struct sip_msg* msg,
1550 1563
 	new_buf=0;
1551 1564
 	received_buf=0;
1552 1565
 	rport_buf=0;
1566
+	via_anchor=0;
1553 1567
 	line_buf=0;
1554 1568
 	via_len=0;
1569
+	path_buf.s=0;
1570
+	path_buf.len=0;
1555 1571
 
1556 1572
 	flags=msg->msg_flags|global_req_flags;
1557 1573
 	/* Calculate message body difference and adjust Content-Length */
... ...
@@ -1569,8 +1585,10 @@ char * build_req_buf_from_sip_req( struct sip_msg* msg,
1569 1585
 	branch.s=msg->add_to_branch_s;
1570 1586
 	branch.len=msg->add_to_branch_len;
1571 1587
 
1588
+	via_anchor=anchor_lump(msg, msg->via1->hdr.s-buf, 0, HDR_VIA_T);
1589
+	if (unlikely(via_anchor==0)) goto error00;
1572 1590
 	line_buf = create_via_hf( &via_len, msg, send_info, &branch);
1573
-	if (!line_buf){
1591
+	if (unlikely(!line_buf)){
1574 1592
 		LOG(L_ERR,"ERROR: build_req_buf_from_sip_req: "
1575 1593
 					"memory allocation failure\n");
1576 1594
 		goto error00;
... ...
@@ -1653,6 +1671,45 @@ after_local_via:
1653 1671
 	}
1654 1672
 
1655 1673
 after_update_via1:
1674
+	/* add route with path content */
1675
+	if(unlikely(!(mode&BUILD_NO_PATH) && msg->path_vec.s &&
1676
+					msg->path_vec.len)){
1677
+		path_buf.len=ROUTE_PREFIX_LEN+msg->path_vec.len+CRLF_LEN;
1678
+		path_buf.s=pkg_malloc(path_buf.len+1);
1679
+		if (unlikely(path_buf.s==0)){
1680
+			LOG(L_ERR, "out of memory\n");
1681
+			ser_error=E_OUT_OF_MEM;
1682
+			goto error00;
1683
+		}
1684
+		memcpy(path_buf.s, ROUTE_PREFIX, ROUTE_PREFIX_LEN);
1685
+		memcpy(path_buf.s+ROUTE_PREFIX_LEN, msg->path_vec.s,
1686
+					msg->path_vec.len);
1687
+		memcpy(path_buf.s+ROUTE_PREFIX_LEN+msg->path_vec.len, CRLF, CRLF_LEN);
1688
+		path_buf.s[path_buf.len]=0;
1689
+		/* insert Route header either before the other routes
1690
+		   (if present & parsed), after the local via or after in front of
1691
+		    the first via if we don't add a local via*/
1692
+		if (msg->route){
1693
+			path_anchor=anchor_lump(msg, msg->route->name.s-buf, 0, 
1694
+									HDR_ROUTE_T);
1695
+		}else if (likely(via_anchor)){
1696
+			path_anchor=via_anchor;
1697
+		}else if (likely(msg->via1)){
1698
+			path_anchor=anchor_lump(msg, msg->via1->hdr.s-buf, 0, 
1699
+									HDR_ROUTE_T);
1700
+		}else{
1701
+			/* if no via1 (theoretically possible for non-sip messages,
1702
+			   e.g. http xmlrpc) */
1703
+			path_anchor=anchor_lump(msg, msg->headers->name.s-buf, 0, 
1704
+									HDR_ROUTE_T);
1705
+		}
1706
+		if (unlikely(path_anchor==0))
1707
+			goto error05;
1708
+		if (unlikely((path_lump=insert_new_lump_after(path_anchor, path_buf.s,
1709
+														path_buf.len,
1710
+														HDR_ROUTE_T))==0))
1711
+			goto error05;
1712
+	}
1656 1713
 	/* compute new msg len and fix overlapping zones*/
1657 1714
 	new_len=len+body_delta+lumps_len(msg, msg->add_rm, send_info)+via_len;
1658 1715
 #ifdef XL_DEBUG
... ...
@@ -1704,8 +1761,6 @@ after_update_via1:
1704 1761
 	/* try to add it before msg. 1st via */
1705 1762
 	/* add first via, as an anchor for second via*/
1706 1763
 	if(likely(line_buf)) {
1707
-		via_anchor=anchor_lump(msg, msg->via1->hdr.s-buf, 0, HDR_VIA_T);
1708
-		if (via_anchor==0) goto error04;
1709 1764
 		if ((via_lump=insert_new_lump_before(via_anchor, line_buf, via_len,
1710 1765
 											HDR_VIA_T))==0)
1711 1766
 			goto error04;
... ...
@@ -1767,6 +1822,8 @@ error03:
1767 1822
 	if (rport_buf) pkg_free(rport_buf);
1768 1823
 error04:
1769 1824
 	if (line_buf) pkg_free(line_buf);
1825
+error05:
1826
+	if (path_buf.s) pkg_free(path_buf.s);
1770 1827
 error00:
1771 1828
 	*returned_len=0;
1772 1829
 	return 0;
... ...
@@ -50,7 +50,8 @@
50 50
 
51 51
 #define BUILD_NO_LOCAL_VIA		(1<<0)
52 52
 #define BUILD_NO_VIA1_UPDATE	(1<<1)
53
-#define BUILD_IN_SHM			(1<<2)
53
+#define BUILD_NO_PATH			(1<<2)
54
+#define BUILD_IN_SHM			(1<<7)
54 55
 
55 56
 #include "parser/msg_parser.h"
56 57
 #include "ip_addr.h"
... ...
@@ -1672,7 +1672,7 @@ int select_branch_uri(str* res, select_t* s, struct sip_msg* msg) {
1672 1672
 		char *c;
1673 1673
 		init_branch_iterator();
1674 1674
 		len = 0;
1675
-		while ((c = next_branch(&l, &q, &dst_uri.s, &dst_uri.len, 0))) {
1675
+		while ((c = next_branch(&l, &q, &dst_uri, 0, 0, 0))) {
1676 1676
 
1677 1677
 			if (s->params[SEL_POS].v.i & SEL_BRANCH_DST_URI) {
1678 1678
 				l = dst_uri.len;
... ...
@@ -1696,7 +1696,7 @@ int select_branch_uri(str* res, select_t* s, struct sip_msg* msg) {
1696 1696
 		init_branch_iterator();
1697 1697
 		res->len = 0;
1698 1698
 		n = 0;
1699
-		while ((c = next_branch(&l, &q, &dst_uri.s, &dst_uri.len, 0))) {
1699
+		while ((c = next_branch(&l, &q, &dst_uri, 0, 0, 0))) {
1700 1700
 			if (s->params[SEL_POS].v.i & SEL_BRANCH_DST_URI) {
1701 1701
 				l = dst_uri.len;
1702 1702
 				c = dst_uri.s;
... ...
@@ -1738,7 +1738,7 @@ int select_branch_uri(str* res, select_t* s, struct sip_msg* msg) {
1738 1738
 		if (n < 0 || n >= nr_branches) 
1739 1739
 			return -1;
1740 1740
 		init_branch_iterator();
1741
-		for (; (c = next_branch(&l, &q, &dst_uri.s, &dst_uri.len, 0)) && n; n--);
1741
+		for (; (c = next_branch(&l, &q, &dst_uri, 0, 0, 0)) && n; n--);
1742 1742
 		if (!c) return 1;
1743 1743
 		
1744 1744
 		if (s->params[SEL_POS].v.i & SEL_BRANCH_DST_URI) {
... ...
@@ -527,6 +527,9 @@ struct sip_msg*  sip_msg_shm_clone( struct sip_msg *org_msg, int *sip_msg_len,
527 527
 		memcpy( p , org_msg->dst_uri.s , org_msg->dst_uri.len);
528 528
 		p += ROUND4(org_msg->dst_uri.len);
529 529
 	}
530
+	/* path_vec is not cloned (it's reset instead) */
531
+	new_msg->path_vec.s=0;
532
+	new_msg->path_vec.len=0;
530 533
 	/* message buffers(org and scratch pad) */
531 534
 	memcpy( p , org_msg->buf, org_msg->len);
532 535
 	/* ZT to be safer */