t_msgbuilder.c 38 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412
  1. /*
  2. * $Id$
  3. *
  4. * message printing
  5. *
  6. * Copyright (C) 2001-2003 FhG Fokus
  7. *
  8. * This file is part of ser, a free SIP server.
  9. *
  10. * ser is free software; you can redistribute it and/or modify
  11. * it under the terms of the GNU General Public License as published by
  12. * the Free Software Foundation; either version 2 of the License, or
  13. * (at your option) any later version
  14. *
  15. * For a license to use the ser software under conditions
  16. * other than those described here, or to purchase support for this
  17. * software, please contact iptel.org by e-mail at the following addresses:
  18. * [email protected]
  19. *
  20. * ser is distributed in the hope that it will be useful,
  21. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  22. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  23. * GNU General Public License for more details.
  24. *
  25. * You should have received a copy of the GNU General Public License
  26. * along with this program; if not, write to the Free Software
  27. * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  28. *
  29. *
  30. * History:
  31. * ----------
  32. * 2003-01-27 next baby-step to removing ZT - PRESERVE_ZT (jiri)
  33. * 2003-02-13 build_uac_request uses proto (andrei)
  34. * 2003-02-28 scratchpad compatibility abandoned (jiri)
  35. * 2003-04-14 build_local no longer checks reply status as it
  36. * is now called before reply status is updated to
  37. * avoid late ACK sending (jiri)
  38. * 2003-10-02 added via_builder set host/port support (andrei)
  39. * 2004-02-11 FIFO/CANCEL + alignments (hash=f(callid,cseq)) (uli+jiri)
  40. * 2004-02-13: t->is_invite and t->local replaced with flags (bogdan)
  41. * 2006-04-21 build_uac_req, assemble_via use struct dest_info now;
  42. * uri2sock replaced with uri2dst (andrei)
  43. * 2006-08-11 build_dlg_ack: use the first dns ip for which a send_sock
  44. * is found (andrei)
  45. * 2007-03-15 build_dls_ack: removed next_hop and replaced by dst to avoid
  46. * resolving nexthop twice (andrei)
  47. * 2007-05-28: build_local_reparse() is introdued: it uses the outgoing
  48. * INVITE as a source to construct a CANCEL or ACK (Miklos)
  49. */
  50. #include "defs.h"
  51. #ifdef EXTRA_DEBUG
  52. #include <assert.h>
  53. #endif
  54. #include "../../comp_defs.h"
  55. #include "../../hash_func.h"
  56. #include "../../globals.h"
  57. #include "t_funcs.h"
  58. #include "../../dprint.h"
  59. #include "../../config.h"
  60. #include "../../parser/parser_f.h"
  61. #include "../../ut.h"
  62. #include "../../parser/msg_parser.h"
  63. #include "../../parser/contact/parse_contact.h"
  64. #include "lw_parser.h"
  65. #include "t_msgbuilder.h"
  66. #include "uac.h"
  67. #ifdef USE_DNS_FAILOVER
  68. #include "../../dns_cache.h"
  69. #include "../../cfg_core.h" /* cfg_get(core, core_cfg, use_dns_failover) */
  70. #endif
  71. /* convenience macros */
  72. #define memapp(_d,_s,_len) \
  73. do{\
  74. memcpy((_d),(_s),(_len));\
  75. (_d) += (_len);\
  76. }while(0)
  77. #define append_mem_block(_d,_s,_len) \
  78. do{\
  79. memcpy((_d),(_s),(_len));\
  80. (_d) += (_len);\
  81. }while(0)
  82. #define append_str(_p,_str) \
  83. do{ \
  84. memcpy((_p), (_str).s, (_str).len); \
  85. (_p)+=(_str).len; \
  86. } while(0)
  87. /* Build a local request based on a previous request; main
  88. customers of this function are local ACK and local CANCEL
  89. */
  90. char *build_local(struct cell *Trans,unsigned int branch,
  91. unsigned int *len, char *method, int method_len, str *to)
  92. {
  93. char *cancel_buf, *p, *via;
  94. unsigned int via_len;
  95. struct hdr_field *hdr;
  96. char branch_buf[MAX_BRANCH_PARAM_LEN];
  97. int branch_len;
  98. str branch_str;
  99. str via_id;
  100. struct hostport hp;
  101. /* init */
  102. via_id.s=0;
  103. via_id.len=0;
  104. /* method, separators, version: "CANCEL sip:[email protected] SIP/2.0" */
  105. *len=SIP_VERSION_LEN + method_len + 2 /* spaces */ + CRLF_LEN;
  106. *len+=Trans->uac[branch].uri.len;
  107. /*via*/
  108. if (!t_calc_branch(Trans, branch,
  109. branch_buf, &branch_len ))
  110. goto error;
  111. branch_str.s=branch_buf;
  112. branch_str.len=branch_len;
  113. set_hostport(&hp, (is_local(Trans))?0:(Trans->uas.request));
  114. #ifdef USE_TCP
  115. if (!is_local(Trans) && ((Trans->uas.request->rcv.proto==PROTO_TCP)
  116. #ifdef USE_TLS
  117. || (Trans->uas.request->rcv.proto==PROTO_TLS)
  118. #endif /* USE_TLS */
  119. )){
  120. if ((via_id.s=id_builder(Trans->uas.request,
  121. (unsigned int*)&via_id.len))==0){
  122. LOG(L_ERR, "ERROR: build_local: id builder failed\n");
  123. /* try to continue without id */
  124. }
  125. }
  126. #endif /* USE_TCP */
  127. via=via_builder(&via_len, &Trans->uac[branch].request.dst,
  128. &branch_str, via_id.s?&via_id:0 , &hp );
  129. /* via_id.s not needed anylonger => free it */
  130. if (via_id.s){
  131. pkg_free(via_id.s);
  132. via_id.s=0;
  133. via_id.len=0;
  134. }
  135. if (!via)
  136. {
  137. LOG(L_ERR, "ERROR: build_local: "
  138. "no via header got from builder\n");
  139. goto error;
  140. }
  141. *len+= via_len;
  142. /*headers*/
  143. *len+=Trans->from.len+Trans->callid.len+to->len+
  144. +Trans->cseq_n.len+1+method_len+CRLF_LEN;
  145. /* copy'n'paste Route headers */
  146. if (!is_local(Trans)) {
  147. for ( hdr=Trans->uas.request->headers ; hdr ; hdr=hdr->next )
  148. if (hdr->type==HDR_ROUTE_T)
  149. *len+=hdr->len;
  150. }
  151. /* User Agent */
  152. if (server_signature) {
  153. *len += USER_AGENT_LEN + CRLF_LEN;
  154. }
  155. /* Content Length, EoM */
  156. *len+=CONTENT_LENGTH_LEN+1 + CRLF_LEN + CRLF_LEN;
  157. cancel_buf=shm_malloc( *len+1 );
  158. if (!cancel_buf)
  159. {
  160. LOG(L_ERR, "ERROR: build_local: cannot allocate memory\n");
  161. goto error01;
  162. }
  163. p = cancel_buf;
  164. append_mem_block( p, method, method_len );
  165. append_mem_block( p, " ", 1 );
  166. append_str( p, Trans->uac[branch].uri );
  167. append_mem_block( p, " " SIP_VERSION CRLF, 1+SIP_VERSION_LEN+CRLF_LEN );
  168. /* insert our via */
  169. append_mem_block(p,via,via_len);
  170. /*other headers*/
  171. append_str( p, Trans->from );
  172. append_str( p, Trans->callid );
  173. append_str( p, *to );
  174. append_str( p, Trans->cseq_n );
  175. append_mem_block( p, " ", 1 );
  176. append_mem_block( p, method, method_len );
  177. append_mem_block( p, CRLF, CRLF_LEN );
  178. if (!is_local(Trans)) {
  179. for ( hdr=Trans->uas.request->headers ; hdr ; hdr=hdr->next )
  180. if(hdr->type==HDR_ROUTE_T) {
  181. append_mem_block(p, hdr->name.s, hdr->len );
  182. }
  183. }
  184. /* User Agent header */
  185. if (server_signature) {
  186. append_mem_block(p,USER_AGENT CRLF, USER_AGENT_LEN+CRLF_LEN );
  187. }
  188. /* Content Length, EoM */
  189. append_mem_block(p, CONTENT_LENGTH "0" CRLF CRLF ,
  190. CONTENT_LENGTH_LEN+1 + CRLF_LEN + CRLF_LEN);
  191. *p=0;
  192. pkg_free(via);
  193. return cancel_buf;
  194. error01:
  195. pkg_free(via);
  196. error:
  197. return NULL;
  198. }
  199. /* Re-parsing version of build_local() function:
  200. * it builds a local CANCEL or ACK (for non-200 response) request based on
  201. * the previous INVITE which was sent out.
  202. *
  203. * Can not be used to build other type of requests!
  204. */
  205. char *build_local_reparse(struct cell *Trans,unsigned int branch,
  206. unsigned int *len, char *method, int method_len, str *to)
  207. {
  208. char *invite_buf, *invite_buf_end;
  209. char *cancel_buf;
  210. char *s, *s1, *d; /* source and destination buffers */
  211. short invite_len;
  212. enum _hdr_types_t hf_type;
  213. int first_via, to_len;
  214. invite_buf = Trans->uac[branch].request.buffer;
  215. invite_len = Trans->uac[branch].request.buffer_len;
  216. if (!invite_buf || !invite_len) {
  217. LOG(L_ERR, "ERROR: build_local_reparse: INVITE is missing\n");
  218. goto error;
  219. }
  220. if ((*invite_buf != 'I') && (*invite_buf != 'i')) {
  221. LOG(L_ERR, "ERROR: build_local_reparse: trying to call build_local_reparse() for a non-INVITE request?\n");
  222. goto error;
  223. }
  224. invite_buf_end = invite_buf + invite_len;
  225. s = invite_buf;
  226. /* Allocate memory for the new message.
  227. The new request will be smaller than the INVITE, so the same size is enough.
  228. I just extend it with the length of new To HF to be sure.
  229. Ugly, but we avoid lots of checks and memory allocations this way */
  230. to_len = to ? to->len : 0;
  231. cancel_buf = shm_malloc(sizeof(char)*(invite_len + to_len));
  232. if (!cancel_buf)
  233. {
  234. LOG(L_ERR, "ERROR: build_local_reparse: cannot allocate shared memory\n");
  235. goto error;
  236. }
  237. d = cancel_buf;
  238. /* method name + space */
  239. append_mem_block(d, method, method_len);
  240. *d = ' ';
  241. d++;
  242. /* skip "INVITE " and copy the rest of the line including CRLF */
  243. s += 7;
  244. s1 = s;
  245. s = eat_line(s, invite_buf_end - s);
  246. append_mem_block(d, s1, s - s1);
  247. /* check every header field name,
  248. we must exclude and modify some of the headers */
  249. first_via = 1;
  250. while (s < invite_buf_end) {
  251. s1 = s;
  252. if ((*s == '\n') || (*s == '\r')) {
  253. /* end of SIP msg */
  254. hf_type = HDR_EOH_T;
  255. } else {
  256. /* parse HF name */
  257. s = lw_get_hf_name(s, invite_buf_end,
  258. &hf_type);
  259. }
  260. switch(hf_type) {
  261. case HDR_CSEQ_T:
  262. /* find the method name and replace it */
  263. while ((s < invite_buf_end)
  264. && ((*s == ':') || (*s == ' ') || (*s == '\t') || ((*s >= '0') && (*s <= '9')))
  265. ) s++;
  266. append_mem_block(d, s1, s - s1);
  267. append_mem_block(d, method, method_len);
  268. append_mem_block(d, CRLF, CRLF_LEN);
  269. s = lw_next_line(s, invite_buf_end);
  270. break;
  271. case HDR_VIA_T:
  272. s = lw_next_line(s, invite_buf_end);
  273. if (first_via) {
  274. /* copy hf */
  275. append_mem_block(d, s1, s - s1);
  276. first_via = 0;
  277. } /* else skip this line, we need olny the first via */
  278. break;
  279. case HDR_TO_T:
  280. if (to_len == 0) {
  281. /* there is no To tag required, just copy paste the header */
  282. s = lw_next_line(s, invite_buf_end);
  283. append_mem_block(d, s1, s - s1);
  284. } else {
  285. /* use the given To HF instead of the original one */
  286. append_mem_block(d, to->s, to->len);
  287. /* move the pointer to the next line */
  288. s = lw_next_line(s, invite_buf_end);
  289. }
  290. break;
  291. case HDR_FROM_T:
  292. case HDR_CALLID_T:
  293. case HDR_ROUTE_T:
  294. case HDR_MAXFORWARDS_T:
  295. /* copy hf */
  296. s = lw_next_line(s, invite_buf_end);
  297. append_mem_block(d, s1, s - s1);
  298. break;
  299. case HDR_REQUIRE_T:
  300. case HDR_PROXYREQUIRE_T:
  301. /* skip this line */
  302. s = lw_next_line(s, invite_buf_end);
  303. break;
  304. case HDR_CONTENTLENGTH_T:
  305. /* copy hf name with 0 value */
  306. append_mem_block(d, s1, s - s1);
  307. append_mem_block(d, ": 0" CRLF, 3 + CRLF_LEN);
  308. /* move the pointer to the next line */
  309. s = lw_next_line(s, invite_buf_end);
  310. break;
  311. case HDR_EOH_T:
  312. /* end of SIP message found */
  313. append_mem_block(d, CRLF, CRLF_LEN);
  314. *len = d - cancel_buf;
  315. /* LOG(L_DBG, "DBG: build_local: %.*s\n", *len, cancel_buf); */
  316. return cancel_buf;
  317. default:
  318. s = lw_next_line(s, invite_buf_end);
  319. if (cfg_get(tm, tm_cfg, ac_extra_hdrs).len
  320. && (s1 + cfg_get(tm, tm_cfg, ac_extra_hdrs).len < invite_buf_end)
  321. && (strncasecmp(s1,
  322. cfg_get(tm, tm_cfg, ac_extra_hdrs).s,
  323. cfg_get(tm, tm_cfg, ac_extra_hdrs).len) == 0)
  324. ) {
  325. append_mem_block(d, s1, s - s1);
  326. } /* else skip this line */
  327. break;
  328. }
  329. }
  330. /* HDR_EOH_T was not found in the buffer, the message is corrupt */
  331. LOG(L_ERR, "ERROR: build_local_reparse: HDR_EOH_T was not found\n");
  332. shm_free(cancel_buf);
  333. error:
  334. LOG(L_ERR, "ERROR: build_local_reparse: cannot build %.*s request\n", method_len, method);
  335. return NULL;
  336. }
  337. typedef struct rte {
  338. rr_t* ptr;
  339. /* 'ptr' above doesn't point to a mem chunk linked to a sip_msg, so it
  340. * won't be free'd along with it => it must be free'd "manually" */
  341. int free_rr;
  342. struct rte* next;
  343. } rte_t;
  344. static inline void free_rte_list(struct rte* list)
  345. {
  346. struct rte* ptr;
  347. while(list) {
  348. ptr = list;
  349. list = list->next;
  350. if (ptr->free_rr)
  351. free_rr(&ptr->ptr);
  352. pkg_free(ptr);
  353. }
  354. }
  355. static inline int calc_routeset_len(struct rte* list, str* contact)
  356. {
  357. struct rte* ptr;
  358. int ret;
  359. if (list || contact) {
  360. ret = ROUTE_PREFIX_LEN + CRLF_LEN;
  361. } else {
  362. return 0;
  363. }
  364. ptr = list;
  365. while(ptr) {
  366. if (ptr != list) {
  367. ret += ROUTE_SEPARATOR_LEN;
  368. }
  369. ret += ptr->ptr->len;
  370. ptr = ptr->next;
  371. }
  372. if (contact) {
  373. if (list) ret += ROUTE_SEPARATOR_LEN;
  374. ret += 2 + contact->len;
  375. }
  376. return ret;
  377. }
  378. /*
  379. * Print the route set
  380. */
  381. static inline char* print_rs(char* p, struct rte* list, str* contact)
  382. {
  383. struct rte* ptr;
  384. if (list || contact) {
  385. memapp(p, ROUTE_PREFIX, ROUTE_PREFIX_LEN);
  386. } else {
  387. return p;
  388. }
  389. ptr = list;
  390. while(ptr) {
  391. if (ptr != list) {
  392. memapp(p, ROUTE_SEPARATOR, ROUTE_SEPARATOR_LEN);
  393. }
  394. memapp(p, ptr->ptr->nameaddr.name.s, ptr->ptr->len);
  395. ptr = ptr->next;
  396. }
  397. if (contact) {
  398. if (list) memapp(p, ROUTE_SEPARATOR, ROUTE_SEPARATOR_LEN);
  399. *p++ = '<';
  400. append_str(p, *contact);
  401. *p++ = '>';
  402. }
  403. memapp(p, CRLF, CRLF_LEN);
  404. return p;
  405. }
  406. /*
  407. * Parse Contact header field body and extract URI
  408. * Does not parse headers !
  409. */
  410. static inline int get_contact_uri(struct sip_msg* msg, str* uri)
  411. {
  412. contact_t* c;
  413. uri->len = 0;
  414. if (!msg->contact) return 1;
  415. if (parse_contact(msg->contact) < 0) {
  416. LOG(L_ERR, "get_contact_uri: Error while parsing Contact body\n");
  417. return -1;
  418. }
  419. c = ((contact_body_t*)msg->contact->parsed)->contacts;
  420. if (!c) {
  421. LOG(L_ERR, "get_contact_uri: Empty body or * contact\n");
  422. return -2;
  423. }
  424. *uri = c->uri;
  425. return 0;
  426. }
  427. /**
  428. * Extract route set from the message (out of Record-Route, if reply, OR
  429. * Route, if request).
  430. * The route set is returned into the "UAC-format" (keep order for Rs, reverse
  431. * RRs).
  432. */
  433. static inline int get_uac_rs(sip_msg_t *msg, int is_req, struct rte **rtset)
  434. {
  435. struct hdr_field* ptr;
  436. rr_t *p, *new_p;
  437. struct rte *t, *head, *old_head;
  438. head = 0;
  439. for (ptr = is_req ? msg->route : msg->record_route; ptr; ptr = ptr->next) {
  440. switch (ptr->type) {
  441. case HDR_RECORDROUTE_T:
  442. if (is_req)
  443. continue;
  444. break;
  445. case HDR_ROUTE_T:
  446. if (! is_req)
  447. continue;
  448. break;
  449. default:
  450. continue;
  451. }
  452. if (parse_rr(ptr) < 0) {
  453. ERR("failed to parse Record-/Route HF (%d).\n", ptr->type);
  454. goto err;
  455. }
  456. p = (rr_t*)ptr->parsed;
  457. while(p) {
  458. if (! (t = (struct rte*)pkg_malloc(sizeof(struct rte)))) {
  459. ERR("out of pkg mem (asked for: %zd).\n", sizeof(struct rte));
  460. goto err;
  461. }
  462. if (is_req) {
  463. /* in case of requests, the sip_msg structure is free'd before
  464. * rte list is evaluated => must do a copy of it */
  465. if (duplicate_rr(&new_p, p) < 0) {
  466. pkg_free(t);
  467. ERR("failed to duplicate RR");
  468. goto err;
  469. }
  470. t->ptr = new_p;
  471. } else {
  472. t->ptr = p;
  473. }
  474. t->free_rr = is_req;
  475. t->next = head;
  476. head = t;
  477. p = p->next;
  478. }
  479. }
  480. if (is_req) {
  481. /* harvesting the R/RR HF above inserts at head, which suites RRs (as
  482. * they must be reversed, anyway), but not Rs => reverse once more */
  483. old_head = head;
  484. head = 0;
  485. while (old_head) {
  486. t = old_head;
  487. old_head = old_head->next;
  488. t->next = head;
  489. head = t;
  490. }
  491. }
  492. *rtset = head;
  493. return 0;
  494. err:
  495. free_rte_list(head);
  496. return -1;
  497. }
  498. static inline unsigned short uri2port(const struct sip_uri *puri)
  499. {
  500. if (puri->port.s) {
  501. return puri->port_no;
  502. } else switch (puri->type) {
  503. case SIP_URI_T:
  504. case TEL_URI_T:
  505. if (puri->transport_val.len == sizeof("TLS") - 1) {
  506. unsigned trans;
  507. trans = puri->transport_val.s[0] | 0x20; trans <<= 8;
  508. trans |= puri->transport_val.s[1] | 0x20; trans <<= 8;
  509. trans |= puri->transport_val.s[2] | 0x20;
  510. if (trans == 0x746C73) /* t l s */
  511. return SIPS_PORT;
  512. }
  513. return SIP_PORT;
  514. case SIPS_URI_T:
  515. case TELS_URI_T:
  516. return SIPS_PORT;
  517. default:
  518. BUG("unexpected URI type %d.\n", puri->type);
  519. }
  520. return 0;
  521. }
  522. /**
  523. * Evaluate if next hop is a strict or loose router, by looking at the
  524. * retr. buffer of the original INVITE.
  525. * Assumes:
  526. * orig_inv is a parsed SIP message;
  527. * rtset is not NULL.
  528. * @return:
  529. * F_RB_NH_LOOSE : next hop was loose router;
  530. * F_RB_NH_STRICT: nh is strict;
  531. * 0 on error.
  532. */
  533. static unsigned long nhop_type(sip_msg_t *orig_inv, rte_t *rtset,
  534. const struct dest_info *dst_inv, str *contact)
  535. {
  536. struct sip_uri puri, topr_uri, lastr_uri, inv_ruri, cont_uri;
  537. struct ip_addr *uri_ia;
  538. union sockaddr_union uri_sau;
  539. unsigned int uri_port, dst_port, inv_port, cont_port, lastr_port;
  540. rte_t *last_r;
  541. #ifdef TM_LOC_ACK_DO_REV_DNS
  542. struct ip_addr ia;
  543. struct hostent *he;
  544. char **alias;
  545. #endif
  546. #define PARSE_URI(_str_, _uri_) \
  547. do { \
  548. /* parse_uri() 0z the puri */ \
  549. if (parse_uri((_str_)->s, \
  550. (_str_)->len, _uri_) < 0) { \
  551. ERR("failed to parse route body '%.*s'.\n", STR_FMT(_str_)); \
  552. return 0; \
  553. } \
  554. } while (0)
  555. #define HAS_LR(_rte_) \
  556. ({ \
  557. PARSE_URI(&(_rte_)->ptr->nameaddr.uri, &puri); \
  558. puri.lr.s; \
  559. })
  560. #define URI_PORT(_puri_, _port) \
  561. do { \
  562. if (! (_port = uri2port(_puri_))) \
  563. return 0; \
  564. } while (0)
  565. /* examine the easy/fast & positive cases foremost */
  566. /* [1] check if 1st route lacks ;lr */
  567. DEBUG("checking lack of ';lr' in 1st route.\n");
  568. if (! HAS_LR(rtset))
  569. return F_RB_NH_STRICT;
  570. topr_uri = puri; /* save 1st route's URI */
  571. /* [2] check if last route shows ;lr */
  572. DEBUG("checking presence of ';lr' in last route.\n");
  573. for (last_r = rtset; last_r->next; last_r = last_r->next)
  574. /* scroll down to last route */
  575. ;
  576. if (HAS_LR(last_r))
  577. return F_RB_NH_LOOSE;
  578. /* [3] 1st route has ;lr -> check if the destination of original INV
  579. * equals the address provided by this route; if does -> loose */
  580. DEBUG("checking INVITE's destination against its first route.\n");
  581. URI_PORT(&topr_uri, uri_port);
  582. if (! (dst_port = su_getport((void *)&dst_inv->to)))
  583. return 0; /* not really expected */
  584. if (dst_port != uri_port)
  585. return F_RB_NH_STRICT;
  586. /* if 1st route contains an IP address, comparing it against .dst */
  587. if ((uri_ia = str2ip(&topr_uri.host))
  588. #ifdef USE_IPV6
  589. || (uri_ia = str2ip6(&topr_uri.host))
  590. #endif
  591. ) {
  592. /* we have an IP address in route -> comparison can go swiftly */
  593. if (init_su(&uri_sau, uri_ia, uri_port) < 0)
  594. return 0; /* not really expected */
  595. if (su_cmp(&uri_sau, (void *)&dst_inv->to))
  596. /* ;lr and sent there */
  597. return F_RB_NH_LOOSE;
  598. else
  599. /* ;lr and NOT sent there (probably sent to RURI address) */
  600. return F_RB_NH_STRICT;
  601. } else {
  602. /*if 1st route contains a name, rev resolve the .dst and compare*/
  603. INFO("Failed to decode string '%.*s' in route set element as IP "
  604. "address. Trying name resolution.\n",STR_FMT(&topr_uri.host));
  605. /* TODO: alternatively, rev name and compare against dest. IP. */
  606. #ifdef TM_LOC_ACK_DO_REV_DNS
  607. ia.af = 0;
  608. su2ip_addr(&ia, (void *)&dst_inv->to);
  609. if (! ia.af)
  610. return 0; /* not really expected */
  611. if ((he = rev_resolvehost(&ia))) {
  612. if ((strlen(he->h_name) == topr_uri.host.len) &&
  613. (memcmp(he->h_name, topr_uri.host.s,
  614. topr_uri.host.len) == 0))
  615. return F_RB_NH_LOOSE;
  616. for (alias = he->h_aliases; *alias; alias ++)
  617. if ((strlen(*alias) == topr_uri.host.len) &&
  618. (memcmp(*alias, topr_uri.host.s,
  619. topr_uri.host.len) == 0))
  620. return F_RB_NH_LOOSE;
  621. return F_RB_NH_STRICT;
  622. } else {
  623. INFO("failed to resolve address '%s' to a name.\n",
  624. ip_addr2a(&ia));
  625. }
  626. #endif
  627. }
  628. WARN("failed to establish with certainty the type of next hop; trying an"
  629. " educated guess.\n");
  630. /* [4] compare (possibly updated) remote target to original RURI; if
  631. * equal, a strict router's address wasn't filled in as RURI -> loose */
  632. DEBUG("checking remote target against INVITE's RURI.\n");
  633. PARSE_URI(contact, &cont_uri);
  634. PARSE_URI(GET_RURI(orig_inv), &inv_ruri);
  635. URI_PORT(&cont_uri, cont_port);
  636. URI_PORT(&inv_ruri, inv_port);
  637. if ((cont_port == inv_port) && (cont_uri.host.len == inv_ruri.host.len) &&
  638. (memcmp(cont_uri.host.s, inv_ruri.host.s, cont_uri.host.len) == 0))
  639. return F_RB_NH_LOOSE;
  640. /* [5] compare (possibly updated) remote target to last route; if equal,
  641. * strict router's address might have been filled as RURI and remote
  642. * target appended to route set -> strict */
  643. DEBUG("checking remote target against INVITE's last route.\n");
  644. PARSE_URI(&last_r->ptr->nameaddr.uri, &lastr_uri);
  645. URI_PORT(&lastr_uri, lastr_port);
  646. if ((cont_port == lastr_port) &&
  647. (cont_uri.host.len == lastr_uri.host.len) &&
  648. (memcmp(cont_uri.host.s, lastr_uri.host.s,
  649. lastr_uri.host.len) == 0))
  650. return F_RB_NH_STRICT;
  651. WARN("failed to establish the type of next hop; assuming loose router.\n");
  652. return F_RB_NH_LOOSE;
  653. #undef PARSE_URI
  654. #undef HAS_LR
  655. #undef URI_PORT
  656. }
  657. /**
  658. * Evaluates the routing elements in locally originated request or reply to
  659. * locally originated request.
  660. * If original INVITE was in-dialog (had to-tag), it uses the
  661. * routes present there (b/c the 2xx for it does not have a RR set, normally).
  662. * Otherwise, use the reply (b/c the INVITE does not have yet the complete
  663. * route set).
  664. *
  665. * @return: negative for failure; out params:
  666. * - list: route set;
  667. * - ruri: RURI to be used in ACK;
  668. * - nexthop: where to first send the ACK.
  669. *
  670. * NOTE: assumes rpl's parsed to EOF!
  671. *
  672. */
  673. static int eval_uac_routing(sip_msg_t *rpl, const struct retr_buf *inv_rb,
  674. str* contact, struct rte **list, str *ruri, str *next_hop)
  675. {
  676. sip_msg_t orig_inv, *sipmsg; /* reparse original INVITE */
  677. rte_t *t, *prev_t, *rtset = NULL;
  678. int is_req;
  679. struct sip_uri puri;
  680. static size_t chklen;
  681. int ret = -1;
  682. /* parse the retr. buffer */
  683. memset(&orig_inv, 0, sizeof(struct sip_msg));
  684. orig_inv.buf = inv_rb->buffer;
  685. orig_inv.len = inv_rb->buffer_len;
  686. DEBUG("reparsing retransmission buffer of original INVITE:\n%.*s\n",
  687. orig_inv.len, orig_inv.buf);
  688. if (parse_msg(orig_inv.buf, orig_inv.len, &orig_inv) != 0) {
  689. ERR("failed to parse retr buffer (weird!): \n%.*s\n", orig_inv.len,
  690. orig_inv.buf);
  691. return -1;
  692. }
  693. /* check if we need to look at request or reply */
  694. if ((parse_headers(&orig_inv, HDR_TO_F, 0) < 0) || (! orig_inv.to)) {
  695. /* the bug is at message assembly */
  696. BUG("failed to parse INVITE retr. buffer and/or extract 'To' HF:"
  697. "\n%.*s\n", orig_inv.len, orig_inv.buf);
  698. goto end;
  699. }
  700. if (((struct to_body *)orig_inv.to->parsed)->tag_value.len) {
  701. DEBUG("building ACK for in-dialog INVITE (using RS in orig. INV.)\n");
  702. if (parse_headers(&orig_inv, HDR_EOH_F, 0) < 0) {
  703. BUG("failed to parse INVITE retr. buffer to EOH:"
  704. "\n%.*s\n", orig_inv.len, orig_inv.buf);
  705. goto end;
  706. }
  707. sipmsg = &orig_inv;
  708. is_req = 1;
  709. } else {
  710. DEBUG("building ACK for out-of-dialog INVITE (using RS in RR set).\n");
  711. sipmsg = rpl;
  712. is_req = 0;
  713. }
  714. /* extract the route set */
  715. if (get_uac_rs(sipmsg, is_req, &rtset) < 0) {
  716. ERR("failed to extract route set.\n");
  717. goto end;
  718. }
  719. if (! rtset) { /* No routes */
  720. *ruri = *contact;
  721. *next_hop = *contact;
  722. } else if (! is_req) { /* out of dialog req. */
  723. if (parse_uri(rtset->ptr->nameaddr.uri.s, rtset->ptr->nameaddr.uri.len,
  724. &puri) < 0) {
  725. ERR("failed to parse first route in set.\n");
  726. goto end;
  727. }
  728. if (puri.lr.s) { /* Next hop is loose router */
  729. *ruri = *contact;
  730. *next_hop = rtset->ptr->nameaddr.uri;
  731. } else { /* Next hop is strict router */
  732. *ruri = rtset->ptr->nameaddr.uri;
  733. *next_hop = *ruri;
  734. /* consume first route, b/c it will be put in RURI */
  735. t = rtset;
  736. rtset = rtset->next;
  737. pkg_free(t);
  738. }
  739. } else {
  740. unsigned long route_flags = inv_rb->flags;
  741. DEBUG("UAC rb flags: 0x%x.\n", (unsigned int)route_flags);
  742. eval_flags:
  743. switch (route_flags & (F_RB_NH_LOOSE|F_RB_NH_STRICT)) {
  744. case 0:
  745. WARN("calculate_hooks() not called when built the local UAC of "
  746. "in-dialog request, or called with empty route set.\n");
  747. /* try to figure out what kind of hop is the next one
  748. * (strict/loose) by reading the original invite */
  749. if ((route_flags = nhop_type(&orig_inv, rtset, &inv_rb->dst,
  750. contact))) {
  751. DEBUG("original request's next hop type evaluated to: 0x%x.\n",
  752. (unsigned int)route_flags);
  753. goto eval_flags;
  754. } else {
  755. ERR("failed to establish what kind of router the next "
  756. "hop is.\n");
  757. goto end;
  758. }
  759. break;
  760. case F_RB_NH_LOOSE:
  761. *ruri = *contact;
  762. *next_hop = rtset->ptr->nameaddr.uri;
  763. break;
  764. case F_RB_NH_STRICT:
  765. /* find ptr to last route body that contains the (possibly) old
  766. * remote target
  767. */
  768. for (t = rtset, prev_t = t; t->next; prev_t = t, t = t->next)
  769. ;
  770. if ((t->ptr->len == contact->len) &&
  771. (memcmp(t->ptr->nameaddr.name.s, contact->s,
  772. contact->len) == 0)){
  773. /* the remote target didn't update -> keep the whole route set,
  774. * including the last entry */
  775. /* do nothing */
  776. } else {
  777. /* trash last entry and replace with new remote target */
  778. free_rte_list(t);
  779. /* compact the rr_t struct along with rte. this way, free'ing
  780. * it can be done along with rte chunk, independent of Route
  781. * header parser's allocator (using pkg/shm) */
  782. chklen = sizeof(struct rte) + sizeof(rr_t);
  783. if (! (t = (struct rte *)pkg_malloc(chklen))) {
  784. ERR("out of pkg memory (%zd required)\n", chklen);
  785. goto end;
  786. }
  787. /* this way, .free_rr is also set to 0 (!!!) */
  788. memset(t, 0, chklen);
  789. ((rr_t *)&t[1])->nameaddr.name = *contact;
  790. ((rr_t *)&t[1])->len = contact->len;
  791. /* chain the new route elem in set */
  792. if (prev_t == rtset)
  793. /*there is only one elem in route set: the remote target*/
  794. rtset = t;
  795. else
  796. prev_t->next = t;
  797. }
  798. *ruri = *GET_RURI(&orig_inv); /* reuse original RURI */
  799. *next_hop = *ruri;
  800. break;
  801. default:
  802. /* probably a mem corruption */
  803. BUG("next hop of original request marked as both loose and strict"
  804. " router (buffer: %.*s).\n", inv_rb->buffer_len,
  805. inv_rb->buffer);
  806. #ifdef EXTRA_DEBUG
  807. abort();
  808. #else
  809. goto end;
  810. #endif
  811. }
  812. }
  813. *list = rtset;
  814. /* all went well */
  815. ret = 0;
  816. end:
  817. free_sip_msg(&orig_inv);
  818. if (ret < 0)
  819. free_rte_list(rtset);
  820. return ret;
  821. }
  822. /*
  823. * The function creates an ACK to 200 OK. Route set will be created
  824. * and parsed and the dst parameter will contain the destination to which
  825. * the request should be send. The function is used by tm when it
  826. * generates local ACK to 200 OK (on behalf of applications using uac)
  827. */
  828. char *build_dlg_ack(struct sip_msg* rpl, struct cell *Trans,
  829. unsigned int branch, str *hdrs, str *body,
  830. unsigned int *len, struct dest_info* dst)
  831. {
  832. char *req_buf, *p, *via;
  833. unsigned int via_len;
  834. char branch_buf[MAX_BRANCH_PARAM_LEN];
  835. int branch_len;
  836. str branch_str;
  837. struct hostport hp;
  838. struct rte* list;
  839. str contact, ruri, *cont;
  840. str next_hop;
  841. str body_len;
  842. str _to, *to = &_to;
  843. #ifdef USE_DNS_FAILOVER
  844. struct dns_srv_handle dns_h;
  845. #endif
  846. #ifdef WITH_AS_SUPPORT
  847. /* With AS support, TM allows for external modules to generate building of
  848. * the ACK; in this case, the ACK's retransmission buffer is built once
  849. * and kept in memory (to help when retransmitted 2xx are received and ACK
  850. * must be resent).
  851. * Allocation of the string raw buffer that holds the ACK is piggy-backed
  852. * with allocation of the retransmission buffer (since both have the same
  853. * life-cycle): both the string buffer and retransm. buffer are placed
  854. * into the same allocated chunk of memory (retr. buffer first, string
  855. * buffer follows).In this case, the 'len' param is used as in-out
  856. * parameter: 'in' to give the extra space needed by the retr. buffer,
  857. * 'out' to return the lenght of the allocated string buffer.
  858. */
  859. unsigned offset = *len;
  860. #endif
  861. if (parse_headers(rpl, HDR_EOH_F, 0) == -1 || !rpl->to) {
  862. ERR("Error while parsing headers.\n");
  863. return 0;
  864. } else {
  865. _to.s = rpl->to->name.s;
  866. _to.len = rpl->to->len;
  867. }
  868. if (get_contact_uri(rpl, &contact) < 0) {
  869. return 0;
  870. }
  871. if (eval_uac_routing(rpl, &Trans->uac[branch].request, &contact,
  872. &list, &ruri, &next_hop) < 0) {
  873. ERR("failed to evaluate routing elements.\n");
  874. return 0;
  875. }
  876. DEBUG("ACK RURI: `%.*s', NH: `%.*s'.\n", STR_FMT(&ruri),
  877. STR_FMT(&next_hop));
  878. if ((contact.s != ruri.s) || (contact.len != ruri.len)) {
  879. /* contact != ruri means that the next
  880. * hop is a strict router, cont will be non-zero
  881. * and print_routeset will append it at the end
  882. * of the route set
  883. */
  884. cont = &contact;
  885. } else {
  886. /* Next hop is a loose router, nothing to append */
  887. cont = 0;
  888. }
  889. /* method, separators, version: "ACK sip:[email protected] SIP/2.0" */
  890. *len = SIP_VERSION_LEN + ACK_LEN + 2 /* spaces */ + CRLF_LEN;
  891. *len += ruri.len;
  892. /* via */
  893. #ifdef USE_DNS_FAILOVER
  894. if (cfg_get(core, core_cfg, use_dns_failover)){
  895. dns_srv_handle_init(&dns_h);
  896. if ((uri2dst(&dns_h , dst, rpl, &next_hop, PROTO_NONE)==0) ||
  897. (dst->send_sock==0)){
  898. dns_srv_handle_put(&dns_h);
  899. LOG(L_ERR, "build_dlg_ack: no socket found\n");
  900. goto error;
  901. }
  902. dns_srv_handle_put(&dns_h); /* not needed any more */
  903. }else{
  904. if ((uri2dst(0 , dst, rpl, &next_hop, PROTO_NONE)==0) ||
  905. (dst->send_sock==0)){
  906. LOG(L_ERR, "build_dlg_ack: no socket found\n");
  907. goto error;
  908. }
  909. }
  910. #else
  911. if ( (uri2dst( dst, rpl, &next_hop, PROTO_NONE)==0) ||
  912. (dst->send_sock==0)){
  913. LOG(L_ERR, "build_dlg_ack: no socket found\n");
  914. goto error;
  915. }
  916. #endif
  917. if (!t_calc_branch(Trans, branch, branch_buf, &branch_len)) goto error;
  918. branch_str.s = branch_buf;
  919. branch_str.len = branch_len;
  920. set_hostport(&hp, 0);
  921. via = via_builder(&via_len, dst, &branch_str, 0, &hp);
  922. if (!via) {
  923. LOG(L_ERR, "build_dlg_ack: No via header got from builder\n");
  924. goto error;
  925. }
  926. *len+= via_len;
  927. /*headers*/
  928. *len += Trans->from.len + Trans->callid.len + to->len + Trans->cseq_n.len + 1 + ACK_LEN + CRLF_LEN;
  929. /* copy'n'paste Route headers */
  930. *len += calc_routeset_len(list, cont);
  931. /* User Agent */
  932. if (server_signature) *len += USER_AGENT_LEN + CRLF_LEN;
  933. /* extra headers */
  934. if (hdrs)
  935. *len += hdrs->len;
  936. /* body */
  937. if (body) {
  938. body_len.s = int2str(body->len, &body_len.len);
  939. *len += body->len;
  940. } else {
  941. body_len.len = 0;
  942. body_len.s = NULL; /*4gcc*/
  943. *len += 1; /* for the (Cont-Len:) `0' */
  944. }
  945. /* Content Length, EoM */
  946. *len += CONTENT_LENGTH_LEN + body_len.len + CRLF_LEN + CRLF_LEN;
  947. #if WITH_AS_SUPPORT
  948. req_buf = shm_malloc(offset + *len + 1);
  949. req_buf += offset;
  950. #else
  951. req_buf = shm_malloc(*len + 1);
  952. #endif
  953. if (!req_buf) {
  954. ERR("Cannot allocate memory (%u+1)\n", *len);
  955. goto error01;
  956. }
  957. p = req_buf;
  958. append_mem_block( p, ACK, ACK_LEN );
  959. append_mem_block( p, " ", 1 );
  960. append_str(p, ruri);
  961. append_mem_block( p, " " SIP_VERSION CRLF, 1 + SIP_VERSION_LEN + CRLF_LEN);
  962. /* insert our via */
  963. append_mem_block(p, via, via_len);
  964. /*other headers*/
  965. append_str(p, Trans->from);
  966. append_str(p, Trans->callid);
  967. append_str(p, *to);
  968. append_str(p, Trans->cseq_n);
  969. append_mem_block( p, " ", 1 );
  970. append_mem_block( p, ACK, ACK_LEN);
  971. append_mem_block(p, CRLF, CRLF_LEN);
  972. /* Routeset */
  973. p = print_rs(p, list, cont);
  974. /* User Agent header */
  975. if (server_signature) {
  976. append_mem_block(p, USER_AGENT CRLF, USER_AGENT_LEN + CRLF_LEN);
  977. }
  978. /* extra headers */
  979. if (hdrs)
  980. append_mem_block(p, hdrs->s, hdrs->len);
  981. /* Content Length, EoH, (body) */
  982. if (body) {
  983. append_mem_block(p, CONTENT_LENGTH, CONTENT_LENGTH_LEN);
  984. append_mem_block(p, body_len.s, body_len.len);
  985. append_mem_block(p, /*end crr. header*/CRLF /*EoH*/CRLF, CRLF_LEN +
  986. CRLF_LEN);
  987. append_mem_block(p, body->s, body->len);
  988. } else {
  989. append_mem_block(p, CONTENT_LENGTH "0" CRLF CRLF,
  990. CONTENT_LENGTH_LEN + 1 + CRLF_LEN + CRLF_LEN);
  991. }
  992. /* EoM */
  993. *p = 0;
  994. pkg_free(via);
  995. free_rte_list(list);
  996. return req_buf;
  997. error01:
  998. pkg_free(via);
  999. error:
  1000. free_rte_list(list);
  1001. return 0;
  1002. }
  1003. /*
  1004. * Convert length of body into asciiz
  1005. */
  1006. static inline int print_content_length(str* dest, str* body)
  1007. {
  1008. static char content_length[10];
  1009. int len;
  1010. int b_len;
  1011. char* tmp;
  1012. /* Print Content-Length */
  1013. b_len=body?body->len:0;
  1014. tmp = int2str(b_len, &len);
  1015. if (len >= sizeof(content_length)) {
  1016. LOG(L_ERR, "ERROR: print_content_length: content_len too big\n");
  1017. dest->s = 0;
  1018. dest->len = 0;
  1019. return -1;
  1020. }
  1021. memcpy(content_length, tmp, len);
  1022. dest->s = content_length;
  1023. dest->len = len;
  1024. return 0;
  1025. }
  1026. /*
  1027. * Convert CSeq number into asciiz
  1028. */
  1029. static inline int print_cseq_num(str* _s, dlg_t* _d)
  1030. {
  1031. static char cseq[INT2STR_MAX_LEN];
  1032. char* tmp;
  1033. int len;
  1034. tmp = int2str(_d->loc_seq.value, &len);
  1035. if (len > sizeof(cseq)) {
  1036. LOG(L_ERR, "print_cseq_num: cseq too big\n");
  1037. return -1;
  1038. }
  1039. memcpy(cseq, tmp, len);
  1040. _s->s = cseq;
  1041. _s->len = len;
  1042. return 0;
  1043. }
  1044. /*
  1045. * Create Via header
  1046. */
  1047. static inline int assemble_via(str* dest, struct cell* t,
  1048. struct dest_info* dst, int branch)
  1049. {
  1050. static char branch_buf[MAX_BRANCH_PARAM_LEN];
  1051. char* via;
  1052. int len;
  1053. unsigned int via_len;
  1054. str branch_str;
  1055. struct hostport hp;
  1056. if (!t_calc_branch(t, branch, branch_buf, &len)) {
  1057. LOG(L_ERR, "ERROR: assemble_via: branch calculation failed\n");
  1058. return -1;
  1059. }
  1060. branch_str.s = branch_buf;
  1061. branch_str.len = len;
  1062. #ifdef XL_DEBUG
  1063. printf("!!!proto: %d\n", sock->proto);
  1064. #endif
  1065. set_hostport(&hp, 0);
  1066. via = via_builder(&via_len, dst, &branch_str, 0, &hp);
  1067. if (!via) {
  1068. LOG(L_ERR, "assemble_via: via building failed\n");
  1069. return -2;
  1070. }
  1071. dest->s = via;
  1072. dest->len = via_len;
  1073. return 0;
  1074. }
  1075. /*
  1076. * Print Request-URI
  1077. */
  1078. static inline char* print_request_uri(char* w, str* method, dlg_t* dialog, struct cell* t, int branch)
  1079. {
  1080. memapp(w, method->s, method->len);
  1081. memapp(w, " ", 1);
  1082. t->uac[branch].uri.s = w;
  1083. t->uac[branch].uri.len = dialog->hooks.request_uri->len;
  1084. memapp(w, dialog->hooks.request_uri->s, dialog->hooks.request_uri->len);
  1085. memapp(w, " " SIP_VERSION CRLF, 1 + SIP_VERSION_LEN + CRLF_LEN);
  1086. return w;
  1087. }
  1088. /*
  1089. * Print To header field
  1090. */
  1091. static inline char* print_to(char* w, dlg_t* dialog, struct cell* t)
  1092. {
  1093. t->to.s = w;
  1094. t->to.len = TO_LEN + dialog->rem_uri.len + CRLF_LEN;
  1095. memapp(w, TO, TO_LEN);
  1096. memapp(w, dialog->rem_uri.s, dialog->rem_uri.len);
  1097. if (dialog->id.rem_tag.len) {
  1098. t->to.len += TOTAG_LEN + dialog->id.rem_tag.len ;
  1099. memapp(w, TOTAG, TOTAG_LEN);
  1100. memapp(w, dialog->id.rem_tag.s, dialog->id.rem_tag.len);
  1101. }
  1102. memapp(w, CRLF, CRLF_LEN);
  1103. return w;
  1104. }
  1105. /*
  1106. * Print From header field
  1107. */
  1108. static inline char* print_from(char* w, dlg_t* dialog, struct cell* t)
  1109. {
  1110. t->from.s = w;
  1111. t->from.len = FROM_LEN + dialog->loc_uri.len + CRLF_LEN;
  1112. memapp(w, FROM, FROM_LEN);
  1113. memapp(w, dialog->loc_uri.s, dialog->loc_uri.len);
  1114. if (dialog->id.loc_tag.len) {
  1115. t->from.len += FROMTAG_LEN + dialog->id.loc_tag.len;
  1116. memapp(w, FROMTAG, FROMTAG_LEN);
  1117. memapp(w, dialog->id.loc_tag.s, dialog->id.loc_tag.len);
  1118. }
  1119. memapp(w, CRLF, CRLF_LEN);
  1120. return w;
  1121. }
  1122. /*
  1123. * Print CSeq header field
  1124. */
  1125. char* print_cseq_mini(char* target, str* cseq, str* method) {
  1126. memapp(target, CSEQ, CSEQ_LEN);
  1127. memapp(target, cseq->s, cseq->len);
  1128. memapp(target, " ", 1);
  1129. memapp(target, method->s, method->len);
  1130. return target;
  1131. }
  1132. static inline char* print_cseq(char* w, str* cseq, str* method, struct cell* t)
  1133. {
  1134. t->cseq_n.s = w;
  1135. /* don't include method name and CRLF -- subsequent
  1136. * local requests ACK/CANCEL will add their own */
  1137. t->cseq_n.len = CSEQ_LEN + cseq->len;
  1138. w = print_cseq_mini(w, cseq, method);
  1139. return w;
  1140. }
  1141. /*
  1142. * Print Call-ID header field
  1143. * created an extra function for pure header field creation, that is used by t_cancel for
  1144. * t_uac_cancel FIFO function.
  1145. */
  1146. char* print_callid_mini(char* target, str callid) {
  1147. memapp(target, CALLID, CALLID_LEN);
  1148. memapp(target, callid.s, callid.len);
  1149. memapp(target, CRLF, CRLF_LEN);
  1150. return target;
  1151. }
  1152. static inline char* print_callid(char* w, dlg_t* dialog, struct cell* t)
  1153. {
  1154. /* begins with CRLF, not included in t->callid, don`t know why...?!? */
  1155. memapp(w, CRLF, CRLF_LEN);
  1156. t->callid.s = w;
  1157. t->callid.len = CALLID_LEN + dialog->id.call_id.len + CRLF_LEN;
  1158. w = print_callid_mini(w, dialog->id.call_id);
  1159. return w;
  1160. }
  1161. /*
  1162. * Create a request
  1163. */
  1164. char* build_uac_req(str* method, str* headers, str* body, dlg_t* dialog, int branch,
  1165. struct cell *t, int* len, struct dest_info* dst)
  1166. {
  1167. char* buf, *w;
  1168. str content_length, cseq, via;
  1169. if (!method || !dialog) {
  1170. LOG(L_ERR, "build_uac_req(): Invalid parameter value\n");
  1171. return 0;
  1172. }
  1173. if (print_content_length(&content_length, body) < 0) {
  1174. LOG(L_ERR, "build_uac_req(): Error while printing content-length\n");
  1175. return 0;
  1176. }
  1177. if (print_cseq_num(&cseq, dialog) < 0) {
  1178. LOG(L_ERR, "build_uac_req(): Error while printing CSeq number\n");
  1179. return 0;
  1180. }
  1181. *len = method->len + 1 + dialog->hooks.request_uri->len + 1 + SIP_VERSION_LEN + CRLF_LEN;
  1182. if (assemble_via(&via, t, dst, branch) < 0) {
  1183. LOG(L_ERR, "build_uac_req(): Error while assembling Via\n");
  1184. return 0;
  1185. }
  1186. *len += via.len;
  1187. *len += TO_LEN + dialog->rem_uri.len
  1188. + (dialog->id.rem_tag.len ? (TOTAG_LEN + dialog->id.rem_tag.len) : 0) + CRLF_LEN; /* To */
  1189. *len += FROM_LEN + dialog->loc_uri.len
  1190. + (dialog->id.loc_tag.len ? (FROMTAG_LEN + dialog->id.loc_tag.len) : 0) + CRLF_LEN; /* From */
  1191. *len += CALLID_LEN + dialog->id.call_id.len + CRLF_LEN; /* Call-ID */
  1192. *len += CSEQ_LEN + cseq.len + 1 + method->len + CRLF_LEN; /* CSeq */
  1193. *len += calculate_routeset_length(dialog); /* Route set */
  1194. *len += CONTENT_LENGTH_LEN + content_length.len + CRLF_LEN; /* Content-
  1195. Length */
  1196. *len += (server_signature ? (USER_AGENT_LEN + CRLF_LEN) : 0); /* Signature */
  1197. *len += (headers ? headers->len : 0); /* Additional headers */
  1198. *len += (body ? body->len : 0); /* Message body */
  1199. *len += CRLF_LEN; /* End of Header */
  1200. buf = shm_malloc(*len + 1);
  1201. if (!buf) {
  1202. LOG(L_ERR, "build_uac_req(): no shmem\n");
  1203. goto error;
  1204. }
  1205. w = buf;
  1206. w = print_request_uri(w, method, dialog, t, branch); /* Request-URI */
  1207. memapp(w, via.s, via.len); /* Top-most Via */
  1208. w = print_to(w, dialog, t); /* To */
  1209. w = print_from(w, dialog, t); /* From */
  1210. w = print_cseq(w, &cseq, method, t); /* CSeq */
  1211. w = print_callid(w, dialog, t); /* Call-ID */
  1212. w = print_routeset(w, dialog); /* Route set */
  1213. /* Content-Length */
  1214. memapp(w, CONTENT_LENGTH, CONTENT_LENGTH_LEN);
  1215. memapp(w, content_length.s, content_length.len);
  1216. memapp(w, CRLF, CRLF_LEN);
  1217. /* Server signature */
  1218. if (server_signature) memapp(w, USER_AGENT CRLF, USER_AGENT_LEN + CRLF_LEN);
  1219. if (headers) memapp(w, headers->s, headers->len);
  1220. memapp(w, CRLF, CRLF_LEN);
  1221. if (body) memapp(w, body->s, body->len);
  1222. #ifdef EXTRA_DEBUG
  1223. assert(w-buf == *len);
  1224. #endif
  1225. pkg_free(via.s);
  1226. return buf;
  1227. error:
  1228. pkg_free(via.s);
  1229. return 0;
  1230. }
  1231. int t_calc_branch(struct cell *t,
  1232. int b, char *branch, int *branch_len)
  1233. {
  1234. return syn_branch ?
  1235. branch_builder( t->hash_index,
  1236. t->label, 0,
  1237. b, branch, branch_len )
  1238. : branch_builder( t->hash_index,
  1239. 0, t->md5,
  1240. b, branch, branch_len );
  1241. }