]> sjero.net Git - linphone/blob - coreapi/sal_eXosip2.c
Merge branch 'upnp'
[linphone] / coreapi / sal_eXosip2.c
1 /*
2 linphone
3 Copyright (C) 2010  Simon MORLAT (simon.morlat@free.fr)
4
5 This program is free software; you can redistribute it and/or
6 modify it under the terms of the GNU General Public License
7 as published by the Free Software Foundation; either version 2
8 of the License, or (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
18 */
19 #ifdef HAVE_CONFIG_H
20 #include "config.h"
21 #endif
22
23 #include "sal_eXosip2.h"
24 #include "offeranswer.h"
25
26 #ifdef ANDROID
27 // Necessary to make it linked
28 static void for_linker() { eXosip_transport_hook_register(NULL); }
29 #endif
30 static bool_t call_failure(Sal *sal, eXosip_event_t *ev);
31
32 static void text_received(Sal *sal, eXosip_event_t *ev);
33
34 static void masquerade_via(osip_message_t *msg, const char *ip, const char *port);
35 static bool_t fix_message_contact(SalOp *op, osip_message_t *request,osip_message_t *last_answer, bool_t expire_last_contact);
36 static void update_contact_from_response(SalOp *op, osip_message_t *response);
37
38 void _osip_list_set_empty(osip_list_t *l, void (*freefunc)(void*)){
39         void *data;
40         while(!osip_list_eol(l,0)) {
41                 data=osip_list_get(l,0);
42                 osip_list_remove(l,0);
43                 if (data) freefunc(data);
44         }
45 }
46
47 void sal_get_default_local_ip(Sal *sal, int address_family,char *ip, size_t iplen){
48         if (eXosip_guess_localip(address_family,ip,iplen)<0){
49                 /*default to something */
50                 strncpy(ip,address_family==AF_INET6 ? "::1" : "127.0.0.1",iplen);
51                 ms_error("Could not find default routable ip address !");
52         }
53 }
54
55
56 static SalOp * sal_find_call(Sal *sal, int cid){
57         const MSList *elem;
58         SalOp *op;
59         for(elem=sal->calls;elem!=NULL;elem=elem->next){
60                 op=(SalOp*)elem->data;
61                 if (op->cid==cid) return op;
62         }
63         return NULL;
64 }
65
66 static void sal_add_call(Sal *sal, SalOp *op){
67         sal->calls=ms_list_append(sal->calls,op);
68 }
69
70 static void sal_remove_call(Sal *sal, SalOp *op){
71         sal->calls=ms_list_remove(sal->calls, op);
72 }
73
74 static SalOp * sal_find_register(Sal *sal, int rid){
75         const MSList *elem;
76         SalOp *op;
77         for(elem=sal->registers;elem!=NULL;elem=elem->next){
78                 op=(SalOp*)elem->data;
79                 if (op->rid==rid) return op;
80         }
81         return NULL;
82 }
83
84 static void sal_add_register(Sal *sal, SalOp *op){
85         sal->registers=ms_list_append(sal->registers,op);
86 }
87
88 static void sal_remove_register(Sal *sal, int rid){
89         MSList *elem;
90         SalOp *op;
91         for(elem=sal->registers;elem!=NULL;elem=elem->next){
92                 op=(SalOp*)elem->data;
93                 if (op->rid==rid) {
94                         sal->registers=ms_list_remove_link(sal->registers,elem);
95                         return;
96                 }
97         }
98 }
99
100 static SalOp * sal_find_other(Sal *sal, osip_message_t *message){
101         const MSList *elem;
102         SalOp *op;
103         osip_call_id_t *callid=osip_message_get_call_id(message);
104         if (callid==NULL) {
105                 ms_error("There is no call-id in this message !");
106                 return NULL;
107         }
108         for(elem=sal->other_transactions;elem!=NULL;elem=elem->next){
109                 op=(SalOp*)elem->data;
110                 if (osip_call_id_match(callid,op->call_id)==0) return op;
111         }
112         return NULL;
113 }
114
115 void sal_add_other(Sal *sal, SalOp *op, osip_message_t *request){
116         osip_call_id_t *callid=osip_message_get_call_id(request);
117         if (callid==NULL) {
118                 ms_error("There is no call id in the request !");
119                 return;
120         }
121         osip_call_id_clone(callid,&op->call_id);
122         sal->other_transactions=ms_list_append(sal->other_transactions,op);
123 }
124
125 static void sal_remove_other(Sal *sal, SalOp *op){
126         sal->other_transactions=ms_list_remove(sal->other_transactions,op);
127 }
128
129
130 static void sal_add_pending_auth(Sal *sal, SalOp *op){
131         sal->pending_auths=ms_list_append(sal->pending_auths,op);
132 }
133
134
135 static void sal_remove_pending_auth(Sal *sal, SalOp *op){
136         sal->pending_auths=ms_list_remove(sal->pending_auths,op);
137 }
138
139 void sal_exosip_fix_route(SalOp *op){
140         if (sal_op_get_route(op)!=NULL){
141                 osip_route_t *rt=NULL;
142                 osip_uri_param_t *lr_param=NULL;
143                 
144                 osip_route_init(&rt);
145                 if (osip_route_parse(rt,sal_op_get_route(op))<0){
146                         ms_warning("Bad route  %s!",sal_op_get_route(op));
147                         sal_op_set_route(op,NULL);
148                 }else{
149                         /* check if the lr parameter is set , if not add it */
150                         osip_uri_uparam_get_byname(rt->url, "lr", &lr_param);
151                         if (lr_param==NULL){
152                                 char *tmproute;
153                                 osip_uri_uparam_add(rt->url,osip_strdup("lr"),NULL);
154                                 osip_route_to_str(rt,&tmproute);
155                                 sal_op_set_route(op,tmproute);
156                                 osip_free(tmproute);
157                         }
158                 }
159                 osip_route_free(rt);
160         }
161 }
162
163 SalOp * sal_op_new(Sal *sal){
164         SalOp *op=ms_new0(SalOp,1);
165         __sal_op_init(op,sal);
166         op->cid=op->did=op->tid=op->rid=op->nid=op->sid=-1;
167         op->result=NULL;
168         op->supports_session_timers=FALSE;
169         op->sdp_offering=TRUE;
170         op->pending_auth=NULL;
171         op->sdp_answer=NULL;
172         op->reinvite=FALSE;
173         op->call_id=NULL;
174         op->replaces=NULL;
175         op->referred_by=NULL;
176         op->masquerade_via=FALSE;
177         op->auto_answer_asked=FALSE;
178         op->auth_info=NULL;
179         op->terminated=FALSE;
180         return op;
181 }
182
183 bool_t sal_call_autoanswer_asked(SalOp *op)
184 {
185         return op->auto_answer_asked;
186 }
187
188 void sal_op_release(SalOp *op){
189         if (op->sdp_answer)
190                 sdp_message_free(op->sdp_answer);
191         if (op->pending_auth)
192                 eXosip_event_free(op->pending_auth);
193         if (op->rid!=-1){
194                 sal_remove_register(op->base.root,op->rid);
195                 eXosip_register_remove(op->rid);
196         }
197         if (op->cid!=-1){
198                 ms_message("Cleaning cid %i",op->cid);
199                 sal_remove_call(op->base.root,op);
200         }
201         if (op->sid!=-1){
202                 sal_remove_out_subscribe(op->base.root,op);
203         }
204         if (op->nid!=-1){
205                 sal_remove_in_subscribe(op->base.root,op);
206                 if (op->call_id)
207                         osip_call_id_free(op->call_id);
208                 op->call_id=NULL;
209         }
210         if (op->pending_auth){
211                 sal_remove_pending_auth(op->base.root,op);
212         }
213         if (op->result)
214                 sal_media_description_unref(op->result);
215         if (op->call_id){
216                 sal_remove_other(op->base.root,op);
217                 osip_call_id_free(op->call_id);
218         }
219         if (op->replaces){
220                 ms_free(op->replaces);
221         }
222         if (op->referred_by){
223                 ms_free(op->referred_by);
224         }
225         if (op->auth_info) {
226                 sal_auth_info_delete(op->auth_info);
227         }
228         __sal_op_free(op);
229 }
230
231 static void _osip_trace_func(char *fi, int li, osip_trace_level_t level, char *chfr, va_list ap){
232         int ortp_level=ORTP_DEBUG;
233         switch(level){
234                 case OSIP_INFO1:
235                 case OSIP_INFO2:
236                 case OSIP_INFO3:
237                 case OSIP_INFO4:
238                         ortp_level=ORTP_MESSAGE;
239                         break;
240                 case OSIP_WARNING:
241                         ortp_level=ORTP_WARNING;
242                         break;
243                 case OSIP_ERROR:
244                 case OSIP_BUG:
245                         ortp_level=ORTP_ERROR;
246                         break;
247                 case OSIP_FATAL:
248                         ortp_level=ORTP_FATAL;
249                         break;
250                 case END_TRACE_LEVEL:
251                         break;
252         }
253         if (ortp_log_level_enabled(level)){
254                 int len=strlen(chfr);
255                 char *chfrdup=ortp_strdup(chfr);
256                 /*need to remove endline*/
257                 if (len>1){
258                         if (chfrdup[len-1]=='\n')
259                                 chfrdup[len-1]='\0';
260                         if (chfrdup[len-2]=='\r')
261                                 chfrdup[len-2]='\0';
262                 }
263                 ortp_logv(ortp_level,chfrdup,ap);
264                 ortp_free(chfrdup);
265         }
266 }
267
268
269 Sal * sal_init(){
270         static bool_t firsttime=TRUE;
271         Sal *sal;
272         if (firsttime){
273                 osip_trace_initialize_func (OSIP_INFO4,&_osip_trace_func);
274                 firsttime=FALSE;
275         }
276         eXosip_init();
277         sal=ms_new0(Sal,1);
278         sal->keepalive_period=30;
279         sal->double_reg=TRUE;
280         sal->use_rports=TRUE;
281         sal->use_101=TRUE;
282         sal->reuse_authorization=FALSE;
283         sal->rootCa = 0;
284         sal->verify_server_certs=TRUE;
285         sal->verify_server_cn=TRUE;
286         sal->expire_old_contact=FALSE;
287         sal->add_dates=FALSE;
288         sal->dscp=-1;
289         return sal;
290 }
291
292 void sal_uninit(Sal* sal){
293         eXosip_quit();
294         if (sal->rootCa)
295                 ms_free(sal->rootCa);
296         ms_free(sal);
297 }
298
299 void sal_set_user_pointer(Sal *sal, void *user_data){
300         sal->up=user_data;
301 }
302
303 void *sal_get_user_pointer(const Sal *sal){
304         return sal->up;
305 }
306
307 static void unimplemented_stub(){
308         ms_warning("Unimplemented SAL callback");
309 }
310
311 void sal_set_callbacks(Sal *ctx, const SalCallbacks *cbs){
312         memcpy(&ctx->callbacks,cbs,sizeof(*cbs));
313         if (ctx->callbacks.call_received==NULL) 
314                 ctx->callbacks.call_received=(SalOnCallReceived)unimplemented_stub;
315         if (ctx->callbacks.call_ringing==NULL) 
316                 ctx->callbacks.call_ringing=(SalOnCallRinging)unimplemented_stub;
317         if (ctx->callbacks.call_accepted==NULL) 
318                 ctx->callbacks.call_accepted=(SalOnCallAccepted)unimplemented_stub;
319         if (ctx->callbacks.call_failure==NULL) 
320                 ctx->callbacks.call_failure=(SalOnCallFailure)unimplemented_stub;
321         if (ctx->callbacks.call_terminated==NULL) 
322                 ctx->callbacks.call_terminated=(SalOnCallTerminated)unimplemented_stub;
323         if (ctx->callbacks.call_released==NULL)
324                 ctx->callbacks.call_released=(SalOnCallReleased)unimplemented_stub;
325         if (ctx->callbacks.call_updating==NULL) 
326                 ctx->callbacks.call_updating=(SalOnCallUpdating)unimplemented_stub;
327         if (ctx->callbacks.auth_requested==NULL) 
328                 ctx->callbacks.auth_requested=(SalOnAuthRequested)unimplemented_stub;
329         if (ctx->callbacks.auth_success==NULL) 
330                 ctx->callbacks.auth_success=(SalOnAuthSuccess)unimplemented_stub;
331         if (ctx->callbacks.register_success==NULL) 
332                 ctx->callbacks.register_success=(SalOnRegisterSuccess)unimplemented_stub;
333         if (ctx->callbacks.register_failure==NULL) 
334                 ctx->callbacks.register_failure=(SalOnRegisterFailure)unimplemented_stub;
335         if (ctx->callbacks.dtmf_received==NULL) 
336                 ctx->callbacks.dtmf_received=(SalOnDtmfReceived)unimplemented_stub;
337         if (ctx->callbacks.notify==NULL)
338                 ctx->callbacks.notify=(SalOnNotify)unimplemented_stub;
339         if (ctx->callbacks.notify_presence==NULL)
340                 ctx->callbacks.notify_presence=(SalOnNotifyPresence)unimplemented_stub;
341         if (ctx->callbacks.subscribe_received==NULL)
342                 ctx->callbacks.subscribe_received=(SalOnSubscribeReceived)unimplemented_stub;
343         if (ctx->callbacks.text_received==NULL)
344                 ctx->callbacks.text_received=(SalOnTextReceived)unimplemented_stub;
345         if (ctx->callbacks.ping_reply==NULL)
346                 ctx->callbacks.ping_reply=(SalOnPingReply)unimplemented_stub;
347 }
348
349 int sal_unlisten_ports(Sal *ctx){
350         if (ctx->running){
351                 eXosip_quit();
352                 eXosip_init();
353                 ctx->running=FALSE;
354         }
355         return 0;
356 }
357
358 int sal_reset_transports(Sal *ctx){
359 #ifdef HAVE_EXOSIP_RESET_TRANSPORTS
360         if (ctx->running){
361                 ms_message("Exosip transports reset.");
362                 eXosip_reset_transports();
363         }
364         return 0;
365 #else
366         ms_warning("sal_reset_transports() not implemented in this version.");
367         return -1;
368 #endif
369 }
370
371
372 static void set_tls_options(Sal *ctx){
373         if (ctx->rootCa) {
374                 eXosip_tls_ctx_t tlsCtx;
375                 memset(&tlsCtx, 0, sizeof(tlsCtx));
376                 snprintf(tlsCtx.root_ca_cert, sizeof(tlsCtx.client.cert), "%s", ctx->rootCa);
377                 eXosip_set_tls_ctx(&tlsCtx);
378         }                       
379 #ifdef HAVE_EXOSIP_TLS_VERIFY_CERTIFICATE
380         eXosip_tls_verify_certificate(ctx->verify_server_certs);
381 #endif
382 #ifdef HAVE_EXOSIP_TLS_VERIFY_CN
383         eXosip_tls_verify_cn(ctx->verify_server_cn);
384 #endif
385 }
386
387 void sal_set_dscp(Sal *ctx, int dscp){
388         ctx->dscp=dscp;
389 #ifdef HAVE_EXOSIP_DSCP
390         if (dscp!=-1)
391                 eXosip_set_option(EXOSIP_OPT_SET_DSCP,&ctx->dscp);
392 #endif
393 }
394
395 int sal_listen_port(Sal *ctx, const char *addr, int port, SalTransport tr, int is_secure){
396         int err;
397         bool_t ipv6;
398         int proto=IPPROTO_UDP;
399         int keepalive = ctx->keepalive_period;
400
401         ctx->transport = tr;
402         switch (tr) {
403         case SalTransportUDP:
404                 proto=IPPROTO_UDP;
405                 eXosip_set_option (EXOSIP_OPT_UDP_KEEP_ALIVE, &keepalive);
406                 break;
407         case SalTransportTCP:
408         case SalTransportTLS:
409                 proto= IPPROTO_TCP;
410                 if (!ctx->tcp_tls_keepalive) keepalive=-1;
411                 eXosip_set_option (EXOSIP_OPT_UDP_KEEP_ALIVE,&keepalive);
412                 set_tls_options(ctx);
413                 break;
414         default:
415                 ms_warning("unexpected proto, using datagram");
416         }
417         /*see if it looks like an IPv6 address*/
418         int use_rports = ctx->use_rports; // Copy char to int to avoid bad alignment
419         eXosip_set_option(EXOSIP_OPT_USE_RPORT,&use_rports);
420         int dont_use_101 = !ctx->use_101; // Copy char to int to avoid bad alignment
421         eXosip_set_option(EXOSIP_OPT_DONT_SEND_101,&dont_use_101);
422         sal_set_dscp(ctx,ctx->dscp);
423         sal_use_dates(ctx,ctx->add_dates);
424
425         ipv6=strchr(addr,':')!=NULL;
426         eXosip_enable_ipv6(ipv6);
427
428         if (is_secure && tr == SalTransportUDP){
429                 ms_fatal("SIP over DTLS is not supported yet.");
430                 return -1;
431         }
432         err=eXosip_listen_addr(proto, addr, port, ipv6 ?  PF_INET6 : PF_INET, is_secure);
433         ctx->running=TRUE;
434         return err;
435 }
436
437 ortp_socket_t sal_get_socket(Sal *ctx){
438 #ifdef HAVE_EXOSIP_GET_SOCKET
439         return eXosip_get_socket(IPPROTO_UDP);
440 #else
441         ms_warning("Sorry, eXosip does not have eXosip_get_socket() method");
442         return -1;
443 #endif
444 }
445
446 void sal_set_user_agent(Sal *ctx, const char *user_agent){
447         eXosip_set_user_agent(user_agent);
448 }
449
450 void sal_use_session_timers(Sal *ctx, int expires){
451         ctx->session_expires=expires;
452 }
453
454 void sal_use_one_matching_codec_policy(Sal *ctx, bool_t one_matching_codec){
455         ctx->one_matching_codec=one_matching_codec;
456 }
457
458 MSList *sal_get_pending_auths(Sal *sal){
459         return ms_list_copy(sal->pending_auths);
460 }
461
462 void sal_use_double_registrations(Sal *ctx, bool_t enabled){
463         ctx->double_reg=enabled;
464 }
465
466 void sal_expire_old_registration_contacts(Sal *ctx, bool_t enabled){
467         ctx->expire_old_contact=enabled;
468 }
469
470 void sal_use_dates(Sal *ctx, bool_t enabled){
471         ctx->add_dates=enabled;
472 #ifdef EXOSIP_OPT_REGISTER_WITH_DATE
473         {
474                 int tmp=enabled;
475                 eXosip_set_option(EXOSIP_OPT_REGISTER_WITH_DATE,&tmp);
476         }
477 #else
478         if (enabled) ms_warning("Exosip does not support EXOSIP_OPT_REGISTER_WITH_DATE option.");
479 #endif
480 }
481
482 void sal_use_rport(Sal *ctx, bool_t use_rports){
483         ctx->use_rports=use_rports;
484 }
485 void sal_use_101(Sal *ctx, bool_t use_101){
486         ctx->use_101=use_101;
487 }
488
489 void sal_set_root_ca(Sal* ctx, const char* rootCa) {
490         if (ctx->rootCa)
491                 ms_free(ctx->rootCa);
492         ctx->rootCa = ms_strdup(rootCa);
493         set_tls_options(ctx);
494 }
495
496 const char *sal_get_root_ca(Sal* ctx) {
497         return ctx->rootCa;
498 }
499
500 void sal_verify_server_certificates(Sal *ctx, bool_t verify){
501         ctx->verify_server_certs=verify;
502 #ifdef HAVE_EXOSIP_TLS_VERIFY_CERTIFICATE
503         eXosip_tls_verify_certificate(verify);
504 #endif
505 }
506
507 void sal_verify_server_cn(Sal *ctx, bool_t verify){
508         ctx->verify_server_cn=verify;
509 #ifdef HAVE_EXOSIP_TLS_VERIFY_CN
510         eXosip_tls_verify_cn(verify);
511 #endif
512 }
513
514 static int extract_received_rport(osip_message_t *msg, const char **received, int *rportval,SalTransport* transport){
515         osip_via_t *via=NULL;
516         osip_generic_param_t *param=NULL;
517         const char *rport=NULL;
518
519         *rportval=5060;
520         *received=NULL;
521         osip_message_get_via(msg,0,&via);
522         if (!via) {
523                 ms_warning("extract_received_rport(): no via.");
524                 return -1;
525         }
526
527         *transport = sal_transport_parse(via->protocol);
528         
529         if (via->port && via->port[0]!='\0')
530                 *rportval=atoi(via->port);
531         
532         osip_via_param_get_byname(via,"rport",&param);
533         if (param) {
534                 rport=param->gvalue;
535                 if (rport && rport[0]!='\0') *rportval=atoi(rport);
536                 *received=via->host;
537         }
538         param=NULL;
539         osip_via_param_get_byname(via,"received",&param);
540         if (param) *received=param->gvalue;
541
542         if (rport==NULL && *received==NULL){
543                 ms_warning("extract_received_rport(): no rport and no received parameters.");
544                 return -1;
545         }
546         return 0;
547 }
548
549 static void set_sdp(osip_message_t *sip,sdp_message_t *msg){
550         int sdplen;
551         char clen[10];
552         char *sdp=NULL;
553         sdp_message_to_str(msg,&sdp);
554         sdplen=strlen(sdp);
555         snprintf(clen,sizeof(clen),"%i",sdplen);
556         osip_message_set_body(sip,sdp,sdplen);
557         osip_message_set_content_type(sip,"application/sdp");
558         osip_message_set_content_length(sip,clen);
559         osip_free(sdp);
560 }
561
562 static void set_sdp_from_desc(osip_message_t *sip, const SalMediaDescription *desc){
563         sdp_message_t *msg=media_description_to_sdp(desc);
564         if (msg==NULL) {
565                 ms_error("Fail to print sdp message !");
566                 return;
567         }
568         set_sdp(sip,msg);
569         sdp_message_free(msg);
570 }
571
572 static void sdp_process(SalOp *h){
573         ms_message("Doing SDP offer/answer process of type %s",h->sdp_offering ? "outgoing" : "incoming");
574         if (h->result){
575                 sal_media_description_unref(h->result);
576         }
577         h->result=sal_media_description_new();
578         if (h->sdp_offering){   
579                 offer_answer_initiate_outgoing(h->base.local_media,h->base.remote_media,h->result);
580         }else{
581                 int i;
582                 if (h->sdp_answer){
583                         sdp_message_free(h->sdp_answer);
584                 }
585                 offer_answer_initiate_incoming(h->base.local_media,h->base.remote_media,h->result,h->base.root->one_matching_codec);
586                 h->sdp_answer=media_description_to_sdp(h->result);
587                 /*once we have generated the SDP answer, we modify the result description for processing by the upper layer.
588                  It should contains media parameters constraint from the remote offer, not our response*/
589                 strcpy(h->result->addr,h->base.remote_media->addr);
590                 h->result->bandwidth=h->base.remote_media->bandwidth;
591                 
592                 for(i=0;i<h->result->n_active_streams;++i){
593                         strcpy(h->result->streams[i].rtp_addr,h->base.remote_media->streams[i].rtp_addr);
594                         strcpy(h->result->streams[i].rtcp_addr,h->base.remote_media->streams[i].rtcp_addr);
595                         h->result->streams[i].ptime=h->base.remote_media->streams[i].ptime;
596                         h->result->streams[i].bandwidth=h->base.remote_media->streams[i].bandwidth;
597                         h->result->streams[i].rtp_port=h->base.remote_media->streams[i].rtp_port;
598                         h->result->streams[i].rtcp_port=h->base.remote_media->streams[i].rtcp_port;
599                         if (h->result->streams[i].proto == SalProtoRtpSavp) {
600                                 h->result->streams[i].crypto[0] = h->base.remote_media->streams[i].crypto[0];
601                         }
602                 }
603         }
604         
605 }
606
607 int sal_call_is_offerer(const SalOp *h){
608         return h->sdp_offering;
609 }
610
611 int sal_call_set_local_media_description(SalOp *h, SalMediaDescription *desc){
612         if (desc)
613                 sal_media_description_ref(desc);
614         if (h->base.local_media)
615                 sal_media_description_unref(h->base.local_media);
616         h->base.local_media=desc;
617         if (h->base.remote_media){
618                 /*case of an incoming call where we modify the local capabilities between the time
619                  * the call is ringing and it is accepted (for example if you want to accept without video*/
620                 /*reset the sdp answer so that it is computed again*/
621                 if (h->sdp_answer){
622                         sdp_message_free(h->sdp_answer);
623                         h->sdp_answer=NULL;
624                 }
625         }
626         return 0;
627 }
628
629 int sal_call(SalOp *h, const char *from, const char *to){
630         int err;
631         const char *route;
632         osip_message_t *invite=NULL;
633         osip_call_id_t *callid;
634         sal_op_set_from(h,from);
635         sal_op_set_to(h,to);
636         sal_exosip_fix_route(h);
637         
638         h->terminated = FALSE;
639
640         route = sal_op_get_route(h);
641         err=eXosip_call_build_initial_invite(&invite,to,from,route,"Phone call");
642         if (err!=0){
643                 ms_error("Could not create call. Error %d (from=%s to=%s route=%s)",
644                                 err, from, to, route);
645                 return -1;
646         }
647         osip_message_set_allow(invite, "INVITE, ACK, CANCEL, OPTIONS, BYE, REFER, NOTIFY, MESSAGE, SUBSCRIBE, INFO");
648         if (h->base.contact){
649                 _osip_list_set_empty(&invite->contacts,(void (*)(void*))osip_contact_free);
650                 osip_message_set_contact(invite,h->base.contact);
651         }
652         if (h->base.root->session_expires!=0){
653                 osip_message_set_header(invite, "Session-expires", "200");
654                 osip_message_set_supported(invite, "timer");
655         }
656         if (h->base.local_media){
657                 h->sdp_offering=TRUE;
658                 set_sdp_from_desc(invite,h->base.local_media);
659         }else h->sdp_offering=FALSE;
660         if (h->replaces){
661                 osip_message_set_header(invite,"Replaces",h->replaces);
662                 if (h->referred_by)
663                         osip_message_set_header(invite,"Referred-By",h->referred_by);
664         }
665         
666         eXosip_lock();
667         err=eXosip_call_send_initial_invite(invite);
668         eXosip_unlock();
669         h->cid=err;
670         if (err<0){
671                 ms_error("Fail to send invite ! Error code %d", err);
672                 return -1;
673         }else{
674                 callid=osip_message_get_call_id(invite);
675                 osip_call_id_to_str(callid,(char **)(&h->base.call_id));
676                 sal_add_call(h->base.root,h);
677         }
678         return 0;
679 }
680
681 int sal_call_notify_ringing(SalOp *h, bool_t early_media){
682         osip_message_t *msg;
683         
684         /*if early media send also 180 and 183 */
685         if (early_media){
686                 msg=NULL;
687                 eXosip_lock();
688                 eXosip_call_build_answer(h->tid,183,&msg);
689                 if (msg){
690                         sdp_process(h);
691                         if (h->sdp_answer){
692                                 set_sdp(msg,h->sdp_answer);
693                                 sdp_message_free(h->sdp_answer);
694                                 h->sdp_answer=NULL;
695                         }
696                         eXosip_call_send_answer(h->tid,183,msg);
697                 }
698                 eXosip_unlock();
699         }else{
700                 eXosip_lock();
701                 eXosip_call_send_answer(h->tid,180,NULL);
702                 eXosip_unlock();
703         }
704         return 0;
705 }
706
707 int sal_call_accept(SalOp * h){
708         osip_message_t *msg;
709         const char *contact=sal_op_get_contact(h);
710         /* sends a 200 OK */
711         int err=eXosip_call_build_answer(h->tid,200,&msg);
712         if (err<0 || msg==NULL){
713                 ms_error("Fail to build answer for call: err=%i",err);
714                 return -1;
715         }
716         if (h->base.root->session_expires!=0){
717                 if (h->supports_session_timers) osip_message_set_supported(msg, "timer");
718         }
719
720         if (contact) {
721                 _osip_list_set_empty(&msg->contacts,(void (*)(void*))osip_contact_free);
722                 osip_message_set_contact(msg,contact);
723         }
724         
725         if (h->base.local_media){
726                 /*this is the case where we received an invite without SDP*/
727                 if (h->sdp_offering) {
728                         set_sdp_from_desc(msg,h->base.local_media);
729                 }else{
730                         if (h->sdp_answer==NULL) sdp_process(h);
731                         if (h->sdp_answer){
732                                 set_sdp(msg,h->sdp_answer);
733                                 sdp_message_free(h->sdp_answer);
734                                 h->sdp_answer=NULL;
735                         }
736                 }
737         }else{
738                 ms_error("You are accepting a call but not defined any media capabilities !");
739         }
740         eXosip_call_send_answer(h->tid,200,msg);
741         return 0;
742 }
743
744 int sal_call_decline(SalOp *h, SalReason reason, const char *redirect){
745         if (reason==SalReasonBusy){
746                 eXosip_lock();
747                 eXosip_call_send_answer(h->tid,486,NULL);
748                 eXosip_unlock();
749         }
750         else if (reason==SalReasonTemporarilyUnavailable){
751                 eXosip_lock();
752                 eXosip_call_send_answer(h->tid,480,NULL);
753                 eXosip_unlock();
754         }else if (reason==SalReasonDoNotDisturb){
755                 eXosip_lock();
756                 eXosip_call_send_answer(h->tid,600,NULL);
757                 eXosip_unlock();
758         }else if (reason==SalReasonMedia){
759                 eXosip_lock();
760                 eXosip_call_send_answer(h->tid,415,NULL);
761                 eXosip_unlock();
762         }else if (redirect!=NULL && reason==SalReasonRedirect){
763                 osip_message_t *msg;
764                 int code;
765                 if (strstr(redirect,"sip:")!=0) code=302;
766                 else code=380;
767                 eXosip_lock();
768                 eXosip_call_build_answer(h->tid,code,&msg);
769                 osip_message_set_contact(msg,redirect);
770                 eXosip_call_send_answer(h->tid,code,msg);
771                 eXosip_unlock();
772         }else sal_call_terminate(h);
773         return 0;
774 }
775
776 SalMediaDescription * sal_call_get_remote_media_description(SalOp *h){
777         return h->base.remote_media;
778 }
779
780 SalMediaDescription * sal_call_get_final_media_description(SalOp *h){
781         if (h->base.local_media && h->base.remote_media && !h->result){
782                 sdp_process(h);
783         }
784         return h->result;
785 }
786
787 int sal_call_set_referer(SalOp *h, SalOp *refered_call){
788         if (refered_call->replaces)
789                 h->replaces=ms_strdup(refered_call->replaces);
790         if (refered_call->referred_by)
791                 h->referred_by=ms_strdup(refered_call->referred_by);
792         return 0;
793 }
794
795 static int send_notify_for_refer(int did, const char *sipfrag){
796         osip_message_t *msg;
797         eXosip_lock();
798         eXosip_call_build_notify(did,EXOSIP_SUBCRSTATE_ACTIVE,&msg);
799         if (msg==NULL){
800                 eXosip_unlock();
801                 ms_warning("Could not build NOTIFY for refer.");
802                 return -1;
803         }
804         osip_message_set_content_type(msg,"message/sipfrag");
805         osip_message_set_header(msg,"Event","refer");
806         osip_message_set_body(msg,sipfrag,strlen(sipfrag));
807         eXosip_call_send_request(did,msg);
808         eXosip_unlock();
809         return 0;
810 }
811
812 /* currently only support to notify trying and 200Ok*/
813 int sal_call_notify_refer_state(SalOp *h, SalOp *newcall){
814         if (newcall==NULL){
815                 /* in progress*/
816                 send_notify_for_refer(h->did,"SIP/2.0 100 Trying\r\n");
817         }
818         else if (newcall->cid!=-1){
819                 if (newcall->did==-1){
820                         /* not yet established*/
821                         if (!newcall->terminated){
822                                 /* in progress*/
823                                 send_notify_for_refer(h->did,"SIP/2.0 100 Trying\r\n");
824                         }
825                 }else{
826                         if (!newcall->terminated){
827                                 if (send_notify_for_refer(h->did,"SIP/2.0 200 Ok\r\n")==-1){
828                                         /* we need previous notify transaction to complete, so buffer the request for later*/
829                                         h->sipfrag_pending="SIP/2.0 200 Ok\r\n";
830                                 }
831                         }
832                 }
833         }
834         return 0;
835 }
836
837 int sal_ping(SalOp *op, const char *from, const char *to){
838         osip_message_t *options=NULL;
839         
840         sal_op_set_from(op,from);
841         sal_op_set_to(op,to);
842         sal_exosip_fix_route(op);
843
844         eXosip_options_build_request (&options, sal_op_get_to(op),
845                         sal_op_get_from(op),sal_op_get_route(op));
846         if (options){
847                 if (op->base.root->session_expires!=0){
848                         osip_message_set_header(options, "Session-expires", "200");
849                         osip_message_set_supported(options, "timer");
850                 }
851                 sal_add_other(sal_op_get_sal(op),op,options);
852                 return eXosip_options_send_request(options);
853         }
854         return -1;
855 }
856
857 int sal_call_refer(SalOp *h, const char *refer_to){
858         osip_message_t *msg=NULL;
859         int err=0;
860         eXosip_lock();
861         eXosip_call_build_refer(h->did,refer_to, &msg);
862         if (msg) err=eXosip_call_send_request(h->did, msg);
863         else err=-1;
864         eXosip_unlock();
865         return err;
866 }
867
868 int sal_call_refer_with_replaces(SalOp *h, SalOp *other_call_h){
869         osip_message_t *msg=NULL;
870         char referto[256]={0};
871         int err=0;
872         eXosip_lock();
873         if (eXosip_call_get_referto(other_call_h->did,referto,sizeof(referto)-1)!=0){
874                 ms_error("eXosip_call_get_referto() failed for did=%i",other_call_h->did);
875                 eXosip_unlock();
876                 return -1;
877         }
878         eXosip_call_build_refer(h->did,referto, &msg);
879         osip_message_set_header(msg,"Referred-By",h->base.from);
880         if (msg) err=eXosip_call_send_request(h->did, msg);
881         else err=-1;
882         eXosip_unlock();
883         return err;
884 }
885
886 SalOp *sal_call_get_replaces(SalOp *h){
887         if (h!=NULL && h->replaces!=NULL){
888                 int cid;
889                 eXosip_lock();
890                 cid=eXosip_call_find_by_replaces(h->replaces);
891                 eXosip_unlock();
892                 if (cid>0){
893                         SalOp *ret=sal_find_call(h->base.root,cid);
894                         return ret;
895                 }
896         }
897         return NULL;
898 }
899
900 int sal_call_send_dtmf(SalOp *h, char dtmf){
901         osip_message_t *msg=NULL;
902         char dtmf_body[128];
903         char clen[10];
904
905         eXosip_lock();
906         eXosip_call_build_info(h->did,&msg);
907         if (msg){
908                 snprintf(dtmf_body, sizeof(dtmf_body), "Signal=%c\r\nDuration=250\r\n", dtmf);
909                 osip_message_set_body(msg,dtmf_body,strlen(dtmf_body));
910                 osip_message_set_content_type(msg,"application/dtmf-relay");
911                 snprintf(clen,sizeof(clen),"%lu",(unsigned long)strlen(dtmf_body));
912                 osip_message_set_content_length(msg,clen);              
913                 eXosip_call_send_request(h->did,msg);
914         }
915         eXosip_unlock();
916         return 0;
917 }
918
919 static void push_auth_to_exosip(const SalAuthInfo *info){
920         const char *userid;
921         if (info->userid==NULL || info->userid[0]=='\0') userid=info->username;
922         else userid=info->userid;
923         ms_message("Authentication info for username [%s], id[%s], realm [%s] added to eXosip", info->username,userid, info->realm);
924         eXosip_add_authentication_info (info->username,userid,
925                                   info->password, NULL,info->realm);
926 }
927 /*
928  * Just for symmetry ;-)
929  */
930 static void pop_auth_from_exosip() {
931         eXosip_clear_authentication_info();
932 }
933
934 int sal_call_terminate(SalOp *h){
935         int err;
936         if (h == NULL) return -1;
937         if (h->auth_info) push_auth_to_exosip(h->auth_info);
938         eXosip_lock();
939         err=eXosip_call_terminate(h->cid,h->did);
940         eXosip_unlock();
941         if (!h->base.root->reuse_authorization) pop_auth_from_exosip();
942         if (err!=0){
943                 ms_warning("Exosip could not terminate the call: cid=%i did=%i", h->cid,h->did);
944         }
945         h->terminated=TRUE;
946         return 0;
947 }
948
949 void sal_op_authenticate(SalOp *h, const SalAuthInfo *info){
950        bool_t terminating=FALSE;
951        if (h->pending_auth && strcmp(h->pending_auth->request->sip_method,"BYE")==0) {
952                terminating=TRUE;
953        }
954        if (h->terminated && !terminating) return;
955
956        if (h->pending_auth){
957                 push_auth_to_exosip(info);
958                 
959         /*FIXME exosip does not take into account this update register message*/
960         /*
961         if (fix_message_contact(h, h->pending_auth->request,h->pending_auth->response)) {
962             
963         };
964         */
965                 update_contact_from_response(h,h->pending_auth->response);
966                 eXosip_lock();
967                 eXosip_default_action(h->pending_auth);
968                 eXosip_unlock();
969                 ms_message("eXosip_default_action() done");
970                 if (!h->base.root->reuse_authorization) pop_auth_from_exosip();
971                 
972                 if (h->auth_info) sal_auth_info_delete(h->auth_info); /*if already exist*/
973                 h->auth_info=sal_auth_info_clone(info); /*store auth info for subsequent request*/
974         }
975 }
976 void sal_op_cancel_authentication(SalOp *h) {
977         if (h->rid >0) {
978                 sal_op_get_sal(h)->callbacks.register_failure(h,SalErrorFailure, SalReasonForbidden,"Authentication failure");
979         } else if (h->cid >0) {
980                 sal_op_get_sal(h)->callbacks.call_failure(h,SalErrorFailure, SalReasonForbidden,"Authentication failure",0);
981         } else {
982                 ms_warning("Auth failure not handled");
983         }
984
985 }
986 static void set_network_origin(SalOp *op, osip_message_t *req){
987         const char *received=NULL;
988         int rport=5060;
989         char origin[64]={0};
990     SalTransport transport;
991         if (extract_received_rport(req,&received,&rport,&transport)!=0){
992                 osip_via_t *via=NULL;
993                 char *tmp;
994                 osip_message_get_via(req,0,&via);
995                 received=osip_via_get_host(via);
996                 tmp=osip_via_get_port(via);
997                 if (tmp) rport=atoi(tmp);
998         }
999     if (transport != SalTransportUDP) {
1000         snprintf(origin,sizeof(origin)-1,"sip:%s:%i",received,rport);
1001     } else {
1002        snprintf(origin,sizeof(origin)-1,"sip:%s:%i;transport=%s",received,rport,sal_transport_to_string(transport)); 
1003     }
1004         __sal_op_set_network_origin(op,origin);
1005 }
1006
1007 static void set_remote_ua(SalOp* op, osip_message_t *req){
1008         if (op->base.remote_ua==NULL){
1009                 osip_header_t *h=NULL;
1010                 osip_message_get_user_agent(req,0,&h);
1011                 if (h){
1012                         op->base.remote_ua=ms_strdup(h->hvalue);
1013                 }
1014         }
1015 }
1016
1017 static void set_replaces(SalOp *op, osip_message_t *req){
1018         osip_header_t *h=NULL;
1019
1020         if (op->replaces){
1021                 ms_free(op->replaces);
1022                 op->replaces=NULL;
1023         }
1024         osip_message_header_get_byname(req,"replaces",0,&h);
1025         if (h){
1026                 if (h->hvalue && h->hvalue[0]!='\0'){
1027                         op->replaces=ms_strdup(h->hvalue);
1028                 }
1029         }
1030 }
1031
1032 static SalOp *find_op(Sal *sal, eXosip_event_t *ev){
1033         if (ev->cid>0){
1034                 return sal_find_call(sal,ev->cid);
1035         }
1036         if (ev->rid>0){
1037                 return sal_find_register(sal,ev->rid);
1038         }
1039         if (ev->sid>0){
1040                 return sal_find_out_subscribe(sal,ev->sid);
1041         }
1042         if (ev->nid>0){
1043                 return sal_find_in_subscribe(sal,ev->nid);
1044         }
1045         if (ev->response) return sal_find_other(sal,ev->response);
1046         else if (ev->request) return sal_find_other(sal,ev->request);
1047         return NULL;
1048 }
1049
1050 static void inc_new_call(Sal *sal, eXosip_event_t *ev){
1051         SalOp *op=sal_op_new(sal);
1052         osip_from_t *from,*to;
1053         osip_call_info_t *call_info;
1054         char *tmp;
1055         sdp_message_t *sdp=eXosip_get_sdp_info(ev->request);
1056         osip_call_id_t *callid=osip_message_get_call_id(ev->request);
1057         osip_call_id_to_str(callid,(char**)(&op->base.call_id));
1058
1059         set_network_origin(op,ev->request);
1060         set_remote_ua(op,ev->request);
1061         set_replaces(op,ev->request);
1062         
1063         if (sdp){
1064                 op->sdp_offering=FALSE;
1065                 op->base.remote_media=sal_media_description_new();
1066                 sdp_to_media_description(sdp,op->base.remote_media);
1067                 sdp_message_free(sdp);
1068         }else op->sdp_offering=TRUE;
1069
1070         from=osip_message_get_from(ev->request);
1071         to=osip_message_get_to(ev->request);
1072         osip_from_to_str(from,&tmp);
1073         sal_op_set_from(op,tmp);
1074         osip_free(tmp);
1075         osip_from_to_str(to,&tmp);
1076         sal_op_set_to(op,tmp);
1077         osip_free(tmp);
1078
1079         osip_message_get_call_info(ev->request,0,&call_info);
1080         if(call_info)
1081         {
1082                 osip_call_info_to_str(call_info,&tmp);
1083                 if( strstr(tmp,"answer-after=") != NULL)
1084                 {
1085                         op->auto_answer_asked=TRUE;
1086                         ms_message("The caller asked to automatically answer the call(Emergency?)\n");
1087                 }
1088                 osip_free(tmp);
1089         }
1090
1091         op->tid=ev->tid;
1092         op->cid=ev->cid;
1093         op->did=ev->did;
1094         sal_add_call(op->base.root,op);
1095         sal->callbacks.call_received(op);
1096 }
1097
1098 static void handle_reinvite(Sal *sal,  eXosip_event_t *ev){
1099         SalOp *op=find_op(sal,ev);
1100         sdp_message_t *sdp;
1101
1102         if (op==NULL) {
1103                 ms_warning("Reinvite for non-existing operation !");
1104                 return;
1105         }
1106         op->reinvite=TRUE;
1107         op->tid=ev->tid;
1108         sdp=eXosip_get_sdp_info(ev->request);
1109         if (op->base.remote_media){
1110                 sal_media_description_unref(op->base.remote_media);
1111                 op->base.remote_media=NULL;
1112         }
1113         if (op->result){
1114                 sal_media_description_unref(op->result);
1115                 op->result=NULL;
1116         }
1117         if (sdp){
1118                 op->sdp_offering=FALSE;
1119                 op->base.remote_media=sal_media_description_new();
1120                 sdp_to_media_description(sdp,op->base.remote_media);
1121                 sdp_message_free(sdp);
1122                 
1123         }else {
1124                 op->sdp_offering=TRUE;
1125         }
1126         sal->callbacks.call_updating(op);
1127 }
1128
1129 static void handle_ack(Sal *sal,  eXosip_event_t *ev){
1130         SalOp *op=find_op(sal,ev);
1131         sdp_message_t *sdp;
1132
1133         if (op==NULL) {
1134                 ms_warning("ack for non-existing call !");
1135                 return;
1136         }
1137         if (op->terminated) {
1138                 ms_warning("ack for terminated call, ignoring");
1139                 return;
1140         }
1141         
1142         if (op->sdp_offering){
1143                 sdp=eXosip_get_sdp_info(ev->ack);
1144                 if (sdp){
1145                         if (op->base.remote_media)
1146                                 sal_media_description_unref(op->base.remote_media);
1147                         op->base.remote_media=sal_media_description_new();
1148                         sdp_to_media_description(sdp,op->base.remote_media);
1149                         sdp_process(op);
1150                         sdp_message_free(sdp);
1151                 }
1152         }
1153         if (op->reinvite){
1154                 op->reinvite=FALSE;
1155         }
1156         sal->callbacks.call_ack(op);
1157 }
1158
1159 static void update_contact_from_response(SalOp *op, osip_message_t *response){
1160         const char *received;
1161         int rport;
1162         SalTransport transport;
1163         if (extract_received_rport(response,&received,&rport,&transport)==0){
1164                 const char *contact=sal_op_get_contact(op);
1165                 if (!contact){
1166                         /*no contact given yet, use from instead*/
1167                         contact=sal_op_get_from(op);
1168                 }
1169                 if (contact){
1170                         SalAddress *addr=sal_address_new(contact);
1171                         char *tmp;
1172                         sal_address_set_domain(addr,received);
1173                         sal_address_set_port_int(addr,rport);
1174                         if (transport!=SalTransportUDP)
1175                                 sal_address_set_transport(addr,transport);
1176                         tmp=sal_address_as_string(addr);
1177                         ms_message("Contact address updated to %s",tmp);
1178                         sal_op_set_contact(op,tmp);
1179                         sal_address_destroy(addr);
1180                         ms_free(tmp);
1181                 }
1182         }
1183 }
1184
1185 static int call_proceeding(Sal *sal, eXosip_event_t *ev){
1186         SalOp *op=find_op(sal,ev);
1187
1188         if (op==NULL || op->terminated==TRUE) {
1189                 ms_warning("This call has been canceled.");
1190                 eXosip_lock();
1191                 eXosip_call_terminate(ev->cid,ev->did);
1192                 eXosip_unlock();
1193                 return -1;
1194         }
1195         if (ev->did>0)
1196                 op->did=ev->did;
1197         op->tid=ev->tid;
1198         
1199         /* update contact if received and rport are set by the server
1200          note: will only be used by remote for next INVITE, if any...*/
1201         update_contact_from_response(op,ev->response);
1202         return 0;
1203 }
1204
1205 static void call_ringing(Sal *sal, eXosip_event_t *ev){
1206         sdp_message_t *sdp;
1207         SalOp *op=find_op(sal,ev);
1208         if (call_proceeding(sal, ev)==-1) return;
1209
1210         set_remote_ua(op,ev->response);
1211         sdp=eXosip_get_sdp_info(ev->response);
1212         if (sdp){
1213                 op->base.remote_media=sal_media_description_new();
1214                 sdp_to_media_description(sdp,op->base.remote_media);
1215                 sdp_message_free(sdp);
1216                 if (op->base.local_media) sdp_process(op);
1217         }
1218         sal->callbacks.call_ringing(op);
1219 }
1220
1221 static void call_accepted(Sal *sal, eXosip_event_t *ev){
1222         sdp_message_t *sdp;
1223         osip_message_t *msg=NULL;
1224         SalOp *op=find_op(sal,ev);
1225         const char *contact;
1226         
1227         if (op==NULL || op->terminated==TRUE) {
1228                 ms_warning("This call has been already terminated.");
1229                 eXosip_lock();
1230                 eXosip_call_terminate(ev->cid,ev->did);
1231                 eXosip_unlock();
1232                 return ;
1233         }
1234
1235         op->did=ev->did;
1236         set_remote_ua(op,ev->response);
1237
1238         sdp=eXosip_get_sdp_info(ev->response);
1239         if (sdp){
1240                 op->base.remote_media=sal_media_description_new();
1241                 sdp_to_media_description(sdp,op->base.remote_media);
1242                 sdp_message_free(sdp);
1243                 if (op->base.local_media) sdp_process(op);
1244         }
1245         eXosip_call_build_ack(ev->did,&msg);
1246         if (msg==NULL) {
1247                 ms_warning("This call has been already terminated.");
1248                 eXosip_lock();
1249                 eXosip_call_terminate(ev->cid,ev->did);
1250                 eXosip_unlock();
1251                 return ;
1252         }
1253         contact=sal_op_get_contact(op);
1254         if (contact) {
1255                 _osip_list_set_empty(&msg->contacts,(void (*)(void*))osip_contact_free);
1256                 osip_message_set_contact(msg,contact);
1257         }
1258         if (op->sdp_answer){
1259                 set_sdp(msg,op->sdp_answer);
1260                 sdp_message_free(op->sdp_answer);
1261                 op->sdp_answer=NULL;
1262         }
1263         eXosip_call_send_ack(ev->did,msg);
1264         sal->callbacks.call_accepted(op);
1265 }
1266
1267 static void call_terminated(Sal *sal, eXosip_event_t *ev){
1268         char *from=NULL;
1269         SalOp *op=find_op(sal,ev);
1270         if (op==NULL){
1271                 ms_warning("Call terminated for already closed call ?");
1272                 return;
1273         }
1274         if (ev->request){
1275                 osip_from_to_str(ev->request->from,&from);
1276         }
1277         sal->callbacks.call_terminated(op,from!=NULL ? from : sal_op_get_from(op));
1278         if (from) osip_free(from);
1279         op->terminated=TRUE;
1280 }
1281
1282 static void call_released(Sal *sal, eXosip_event_t *ev){
1283         SalOp *op=find_op(sal,ev);
1284         if (op==NULL){
1285                 ms_warning("No op associated to this call_released()");
1286                 return;
1287         }
1288         if (!op->terminated){
1289                 /* no response received so far */
1290                 call_failure(sal,ev);
1291         }
1292         sal->callbacks.call_released(op);
1293 }
1294
1295 static int get_auth_data_from_response(osip_message_t *resp, const char **realm, const char **username){
1296         const char *prx_realm=NULL,*www_realm=NULL;
1297         osip_proxy_authenticate_t *prx_auth;
1298         osip_www_authenticate_t *www_auth;
1299         
1300         *username=osip_uri_get_username(resp->from->url);
1301         prx_auth=(osip_proxy_authenticate_t*)osip_list_get(&resp->proxy_authenticates,0);
1302         www_auth=(osip_proxy_authenticate_t*)osip_list_get(&resp->www_authenticates,0);
1303         if (prx_auth!=NULL)
1304                 prx_realm=osip_proxy_authenticate_get_realm(prx_auth);
1305         if (www_auth!=NULL)
1306                 www_realm=osip_www_authenticate_get_realm(www_auth);
1307
1308         if (prx_realm){
1309                 *realm=prx_realm;
1310         }else if (www_realm){
1311                 *realm=www_realm;
1312         }else{
1313                 return -1;
1314         }
1315         return 0;
1316 }
1317
1318 static int get_auth_data_from_request(osip_message_t *msg, const char **realm, const char **username){
1319         osip_authorization_t *auth=NULL;
1320         osip_proxy_authorization_t *prx_auth=NULL;
1321         
1322         *username=osip_uri_get_username(msg->from->url);
1323         osip_message_get_authorization(msg, 0, &auth);
1324         if (auth){
1325                 *realm=osip_authorization_get_realm(auth);
1326                 return 0;
1327         }
1328         osip_message_get_proxy_authorization(msg,0,&prx_auth);
1329         if (prx_auth){
1330                 *realm=osip_proxy_authorization_get_realm(prx_auth);
1331                 return 0;
1332         }
1333         return -1;
1334 }
1335
1336 static int get_auth_data(eXosip_event_t *ev, const char **realm, const char **username){
1337         if (ev->response && get_auth_data_from_response(ev->response,realm,username)==0) return 0;
1338         if (ev->request && get_auth_data_from_request(ev->request,realm,username)==0) return 0;
1339         return -1;
1340 }
1341
1342 int sal_op_get_auth_requested(SalOp *op, const char **realm, const char **username){
1343         if (op->pending_auth){
1344                 return get_auth_data(op->pending_auth,realm,username);
1345         }
1346         return -1;
1347 }
1348
1349 static bool_t process_authentication(Sal *sal, eXosip_event_t *ev){
1350         SalOp *op;
1351         const char *username,*realm;
1352         op=find_op(sal,ev);
1353         if (op==NULL){
1354                 ms_warning("No operation associated with this authentication !");
1355                 return TRUE;
1356         }
1357         if (get_auth_data(ev,&realm,&username)==0){
1358                 if (op->pending_auth!=NULL){
1359                         eXosip_event_free(op->pending_auth);
1360                         op->pending_auth=ev;
1361                 }else{
1362                         op->pending_auth=ev;
1363                         sal_add_pending_auth(sal,op);
1364                 }
1365                 
1366                 sal->callbacks.auth_requested(op,realm,username);
1367                 return FALSE;
1368         }
1369         return TRUE;
1370 }
1371
1372 static void authentication_ok(Sal *sal, eXosip_event_t *ev){
1373         SalOp *op;
1374         const char *username,*realm;
1375         op=find_op(sal,ev);
1376         if (op==NULL){
1377                 ms_warning("No operation associated with this authentication_ok!");
1378                 return ;
1379         }
1380         if (op->pending_auth){
1381                 eXosip_event_free(op->pending_auth);
1382                 sal_remove_pending_auth(sal,op);
1383                 op->pending_auth=NULL;
1384         }
1385         if (get_auth_data(ev,&realm,&username)==0){
1386                 sal->callbacks.auth_success(op,realm,username);
1387         }
1388 }
1389
1390 static bool_t call_failure(Sal *sal, eXosip_event_t *ev){
1391         SalOp *op;
1392         int code=0;
1393         char* computedReason=NULL;
1394         const char *reason=NULL;
1395         SalError error=SalErrorUnknown;
1396         SalReason sr=SalReasonUnknown;
1397         
1398
1399         op=(SalOp*)find_op(sal,ev);
1400
1401         if (op==NULL) {
1402                 ms_warning("Call failure reported for a closed call, ignored.");
1403                 return TRUE;
1404         }
1405
1406         if (ev->response){
1407                 code=osip_message_get_status_code(ev->response);
1408                 reason=osip_message_get_reason_phrase(ev->response);
1409                 osip_header_t *h=NULL;
1410                 if (!osip_message_header_get_byname(    ev->response
1411                                                                                         ,"Reason"
1412                                                                                         ,0
1413                                                                                         ,&h)) {
1414                         computedReason = ms_strdup_printf("%s %s",reason,osip_header_get_value(h));
1415                         reason = computedReason;
1416
1417                 }
1418         }
1419         switch(code)
1420         {
1421                 case 401:
1422                 case 407:
1423                         return process_authentication(sal,ev);
1424                         break;
1425                 case 400:
1426                         error=SalErrorUnknown;
1427                 break;
1428                 case 404:
1429                         error=SalErrorFailure;
1430                         sr=SalReasonNotFound;
1431                 break;
1432                 case 415:
1433                         error=SalErrorFailure;
1434                         sr=SalReasonMedia;
1435                 break;
1436                 case 422:
1437                         eXosip_default_action(ev);
1438                         return TRUE;
1439                 break;
1440                 case 480:
1441                         error=SalErrorFailure;
1442                         sr=SalReasonTemporarilyUnavailable;
1443                 case 486:
1444                         error=SalErrorFailure;
1445                         sr=SalReasonBusy;
1446                 break;
1447                 case 487:
1448                 break;
1449                 case 600:
1450                         error=SalErrorFailure;
1451                         sr=SalReasonDoNotDisturb;
1452                 break;
1453                 case 603:
1454                         error=SalErrorFailure;
1455                         sr=SalReasonDeclined;
1456                 break;
1457                 default:
1458                         if (code>0){
1459                                 error=SalErrorFailure;
1460                                 sr=SalReasonUnknown;
1461                         }else error=SalErrorNoResponse;
1462         }
1463         op->terminated=TRUE;
1464         sal->callbacks.call_failure(op,error,sr,reason,code);
1465         if (computedReason != NULL){
1466                 ms_free(computedReason);
1467         }
1468         return TRUE;
1469 }
1470
1471 /* Request remote side to send us VFU */
1472 void sal_call_send_vfu_request(SalOp *h){
1473         osip_message_t *msg=NULL;
1474         char info_body[] =
1475                         "<?xml version=\"1.0\" encoding=\"utf-8\" ?>"
1476                          "<media_control>"
1477                          "  <vc_primitive>"
1478                          "    <to_encoder>"
1479                          "      <picture_fast_update></picture_fast_update>"
1480                          "    </to_encoder>"
1481                          "  </vc_primitive>"
1482                          "</media_control>";
1483
1484         char clen[10];
1485
1486         eXosip_lock();
1487         eXosip_call_build_info(h->did,&msg);
1488         if (msg){
1489                 osip_message_set_body(msg,info_body,strlen(info_body));
1490                 osip_message_set_content_type(msg,"application/media_control+xml");
1491                 snprintf(clen,sizeof(clen),"%lu",(unsigned long)strlen(info_body));
1492                 osip_message_set_content_length(msg,clen);
1493                 eXosip_call_send_request(h->did,msg);
1494                 ms_message("Sending VFU request !");
1495         }
1496         eXosip_unlock();
1497 }
1498
1499 static void process_media_control_xml(Sal *sal, eXosip_event_t *ev){
1500         SalOp *op=find_op(sal,ev);
1501         osip_body_t *body=NULL;
1502
1503         if (op==NULL){
1504                 ms_warning("media control xml received without operation context!");
1505                 return ;
1506         }
1507         
1508         osip_message_get_body(ev->request,0,&body);
1509         if (body && body->body!=NULL &&
1510                 strstr(body->body,"picture_fast_update")){
1511                 osip_message_t *ans=NULL;
1512                 ms_message("Receiving VFU request !");
1513                 if (sal->callbacks.vfu_request){
1514                         sal->callbacks.vfu_request(op);
1515                         eXosip_call_build_answer(ev->tid,200,&ans);
1516                         if (ans)
1517                                 eXosip_call_send_answer(ev->tid,200,ans);
1518                         return;
1519                 }
1520         }
1521         /*in all other cases we must say it is not implemented.*/
1522         {
1523                 osip_message_t *ans=NULL;
1524                 eXosip_lock();
1525                 eXosip_call_build_answer(ev->tid,501,&ans);
1526                 if (ans)
1527                         eXosip_call_send_answer(ev->tid,501,ans);
1528                 eXosip_unlock();
1529         }
1530 }
1531
1532 static void process_dtmf_relay(Sal *sal, eXosip_event_t *ev){
1533         SalOp *op=find_op(sal,ev);
1534         osip_body_t *body=NULL;
1535
1536         if (op==NULL){
1537                 ms_warning("media dtmf relay received without operation context!");
1538                 return ;
1539         }
1540         
1541         osip_message_get_body(ev->request,0,&body);
1542         if (body && body->body!=NULL){
1543                 osip_message_t *ans=NULL;
1544                 const char *name=strstr(body->body,"Signal");
1545                 if (name==NULL) name=strstr(body->body,"signal");
1546                 if (name==NULL) {
1547                         ms_warning("Could not extract the dtmf name from the SIP INFO.");
1548                 }else{
1549                         char tmp[2];
1550                         name+=strlen("signal");
1551                         if (sscanf(name," = %1s",tmp)==1){
1552                                 ms_message("Receiving dtmf %s via SIP INFO.",tmp);
1553                                 if (sal->callbacks.dtmf_received != NULL)
1554                                         sal->callbacks.dtmf_received(op, tmp[0]);
1555                         }
1556                 }
1557                 eXosip_lock();
1558                 eXosip_call_build_answer(ev->tid,200,&ans);
1559                 if (ans)
1560                         eXosip_call_send_answer(ev->tid,200,ans);
1561                 eXosip_unlock();
1562         }
1563 }
1564
1565 static void fill_options_answer(osip_message_t *options){
1566         osip_message_set_allow(options,"INVITE, ACK, BYE, CANCEL, OPTIONS, MESSAGE, SUBSCRIBE, NOTIFY, INFO");
1567         osip_message_set_accept(options,"application/sdp");
1568 }
1569
1570 static void process_refer(Sal *sal, SalOp *op, eXosip_event_t *ev){
1571         osip_header_t *h=NULL;
1572         osip_message_t *ans=NULL;
1573         ms_message("Receiving REFER request !");
1574         osip_message_header_get_byname(ev->request,"Refer-To",0,&h);
1575
1576         if (h){
1577                 osip_from_t *from=NULL;
1578                 char *tmp;
1579                 osip_from_init(&from);
1580         
1581                 if (osip_from_parse(from,h->hvalue)==0){
1582                         if (op ){
1583                                 osip_uri_header_t *uh=NULL;
1584                                 osip_header_t *referred_by=NULL;
1585                                 osip_uri_header_get_byname(&from->url->url_headers,(char*)"Replaces",&uh);
1586                                 if (uh!=NULL && uh->gvalue && uh->gvalue[0]!='\0'){
1587                                         ms_message("Found replaces in Refer-To");
1588                                         if (op->replaces){
1589                                                 ms_free(op->replaces);
1590                                         }
1591                                         op->replaces=ms_strdup(uh->gvalue);
1592                                 }
1593                                 osip_message_header_get_byname(ev->request,"Referred-By",0,&referred_by);
1594                                 if (referred_by && referred_by->hvalue && referred_by->hvalue[0]!='\0'){
1595                                         if (op->referred_by)
1596                                                 ms_free(op->referred_by);
1597                                         op->referred_by=ms_strdup(referred_by->hvalue);
1598                                 }
1599                         }
1600                         osip_uri_header_freelist(&from->url->url_headers);
1601                         osip_from_to_str(from,&tmp);
1602                         sal->callbacks.refer_received(sal,op,tmp);
1603                         osip_free(tmp);
1604                         osip_from_free(from);
1605                 }
1606                 eXosip_lock();
1607                 eXosip_call_build_answer(ev->tid,202,&ans);
1608                 if (ans)
1609                         eXosip_call_send_answer(ev->tid,202,ans);
1610                 eXosip_unlock();
1611         }
1612         else
1613         {
1614                 ms_warning("cannot do anything with the refer without destination\n");
1615         }
1616 }
1617
1618 static void process_notify(Sal *sal, eXosip_event_t *ev){
1619         osip_header_t *h=NULL;
1620         char *from=NULL;
1621         SalOp *op=find_op(sal,ev);
1622         osip_message_t *ans=NULL;
1623
1624         ms_message("Receiving NOTIFY request !");
1625         osip_from_to_str(ev->request->from,&from);
1626         osip_message_header_get_byname(ev->request,"Event",0,&h);
1627         if(h){
1628                 osip_body_t *body=NULL;
1629                 //osip_content_type_t *ct=NULL;
1630                 osip_message_get_body(ev->request,0,&body);
1631                 //ct=osip_message_get_content_type(ev->request);
1632                 if (h->hvalue && strcasecmp(h->hvalue,"refer")==0){
1633                         /*special handling of refer events*/
1634                         if (body && body->body){
1635                                 osip_message_t *msg;
1636                                 osip_message_init(&msg);
1637                                 if (osip_message_parse_sipfrag(msg,body->body,strlen(body->body))==0){
1638                                         int code=osip_message_get_status_code(msg);
1639                                         if (code==100){
1640                                                 sal->callbacks.notify_refer(op,SalReferTrying);
1641                                         }else if (code==200){
1642                                                 sal->callbacks.notify_refer(op,SalReferSuccess);
1643                                         }else if (code>=400){
1644                                                 sal->callbacks.notify_refer(op,SalReferFailed);
1645                                         }
1646                                 }
1647                                 osip_message_free(msg);
1648                         }
1649                 }else{
1650                         /*generic handling*/
1651                         sal->callbacks.notify(op,from,h->hvalue);
1652                 }
1653         }
1654         /*answer that we received the notify*/
1655         eXosip_lock();
1656         eXosip_call_build_answer(ev->tid,200,&ans);
1657         if (ans)
1658                 eXosip_call_send_answer(ev->tid,200,ans);
1659         eXosip_unlock();
1660         osip_free(from);
1661 }
1662
1663 static void call_message_new(Sal *sal, eXosip_event_t *ev){
1664         osip_message_t *ans=NULL;
1665         if (ev->request){
1666                 if (MSG_IS_INFO(ev->request)){
1667                         osip_content_type_t *ct;
1668                         ct=osip_message_get_content_type(ev->request);
1669                         if (ct && ct->subtype){
1670                                 if (strcmp(ct->subtype,"media_control+xml")==0)
1671                                         process_media_control_xml(sal,ev);
1672                                 else if (strcmp(ct->subtype,"dtmf-relay")==0)
1673                                         process_dtmf_relay(sal,ev);
1674                                 else {
1675                                         ms_message("Unhandled SIP INFO.");
1676                                         /*send an "Not implemented" answer*/
1677                                         eXosip_lock();
1678                                         eXosip_call_build_answer(ev->tid,501,&ans);
1679                                         if (ans)
1680                                                 eXosip_call_send_answer(ev->tid,501,ans);
1681                                         eXosip_unlock();
1682                                 }
1683                         }else{
1684                                 /*empty SIP INFO, probably to test we are alive. Send an empty answer*/
1685                                 eXosip_lock();
1686                                 eXosip_call_build_answer(ev->tid,200,&ans);
1687                                 if (ans)
1688                                         eXosip_call_send_answer(ev->tid,200,ans);
1689                                 eXosip_unlock();
1690                         }
1691                 }else if(MSG_IS_MESSAGE(ev->request)){
1692                         /* SIP messages could be received into call */
1693                         text_received(sal, ev);
1694                         eXosip_lock();
1695                         eXosip_call_build_answer(ev->tid,200,&ans);
1696                         if (ans)
1697                                 eXosip_call_send_answer(ev->tid,200,ans);
1698                         eXosip_unlock();
1699                 }else if(MSG_IS_REFER(ev->request)){
1700                         SalOp *op=find_op(sal,ev);
1701                         
1702                         ms_message("Receiving REFER request !");
1703                         process_refer(sal,op,ev);
1704                 }else if(MSG_IS_NOTIFY(ev->request)){
1705                         process_notify(sal,ev);
1706                 }else if (MSG_IS_OPTIONS(ev->request)){
1707                         eXosip_lock();
1708                         eXosip_call_build_answer(ev->tid,200,&ans);
1709                         if (ans){
1710                                 fill_options_answer(ans);
1711                                 eXosip_call_send_answer(ev->tid,200,ans);
1712                         }
1713                         eXosip_unlock();
1714                 }
1715         }else ms_warning("call_message_new: No request ?");
1716 }
1717
1718 static void inc_update(Sal *sal, eXosip_event_t *ev){
1719         osip_message_t *msg=NULL;
1720         ms_message("Processing incoming UPDATE");
1721         eXosip_lock();
1722         eXosip_message_build_answer(ev->tid,200,&msg);
1723         if (msg!=NULL)
1724                 eXosip_message_send_answer(ev->tid,200,msg);
1725         eXosip_unlock();
1726 }
1727
1728 static bool_t comes_from_local_if(osip_message_t *msg){
1729         osip_via_t *via=NULL;
1730         osip_message_get_via(msg,0,&via);
1731         if (via){
1732                 const char *host;
1733                 host=osip_via_get_host(via);
1734                 if (strcmp(host,"127.0.0.1")==0 || strcmp(host,"::1")==0){
1735                         osip_generic_param_t *param=NULL;
1736                         osip_via_param_get_byname(via,"received",&param);
1737                         if (param==NULL) return TRUE;
1738                         if (param->gvalue &&
1739                                 (strcmp(param->gvalue,"127.0.0.1")==0 || strcmp(param->gvalue,"::1")==0)){
1740                                 return TRUE;
1741                         }
1742                 }
1743         }
1744         return FALSE;
1745 }
1746
1747 static void text_received(Sal *sal, eXosip_event_t *ev){
1748         osip_body_t *body=NULL;
1749         char *from=NULL,*msg=NULL;
1750         osip_content_type_t* content_type;
1751         osip_uri_param_t* external_body_url; 
1752         char unquoted_external_body_url [256];
1753         int external_body_size=0;
1754         SalMessage salmsg;
1755         char message_id[256]={0};
1756         
1757         content_type= osip_message_get_content_type(ev->request);
1758         if (!content_type) {
1759                 ms_error("Could not get message because no content type");
1760                 return;
1761         }
1762         osip_from_to_str(ev->request->from,&from);
1763         if (content_type->type 
1764                 && strcmp(content_type->type, "text")==0 
1765                 && content_type->subtype
1766                 && strcmp(content_type->subtype, "plain")==0 ) {
1767                 osip_message_get_body(ev->request,0,&body);
1768                 if (body==NULL){
1769                         ms_error("Could not get text message from SIP body");
1770                         osip_free(from);
1771                         return;
1772                 }
1773                 msg=body->body;
1774         }else if (content_type->type 
1775                   && strcmp(content_type->type, "message")==0 
1776                   && content_type->subtype
1777                   && strcmp(content_type->subtype, "external-body")==0 ) {
1778                 
1779                 osip_content_type_param_get_byname(content_type, "URL", &external_body_url);
1780                 /*remove both first and last character*/
1781                 strncpy(unquoted_external_body_url
1782                                 ,&external_body_url->gvalue[1]
1783                                 ,external_body_size=MIN(strlen(external_body_url->gvalue)-1,sizeof(unquoted_external_body_url)));
1784                 unquoted_external_body_url[external_body_size-1]='\0';
1785         } else {
1786                 ms_warning("Unsupported content type [%s/%s]",content_type->type,content_type->subtype);
1787                 osip_free(from);
1788                 return;
1789         }
1790         snprintf(message_id,sizeof(message_id)-1,"%s%s",ev->request->call_id->number,ev->request->cseq->number);
1791         
1792         salmsg.from=from;
1793         salmsg.text=msg;
1794         salmsg.url=external_body_size>0 ? unquoted_external_body_url : NULL;
1795         salmsg.message_id=message_id;
1796         sal->callbacks.text_received(sal,&salmsg);
1797         osip_free(from);
1798 }
1799
1800
1801
1802 static void other_request(Sal *sal, eXosip_event_t *ev){
1803         ms_message("in other_request");
1804         if (ev->request==NULL) return;
1805         if (strcmp(ev->request->sip_method,"MESSAGE")==0){
1806                 text_received(sal,ev);
1807                 eXosip_message_send_answer(ev->tid,200,NULL);
1808         }else if (strcmp(ev->request->sip_method,"OPTIONS")==0){
1809                 osip_message_t *options=NULL;
1810                 eXosip_options_build_answer(ev->tid,200,&options);
1811                 fill_options_answer(options);
1812                 eXosip_options_send_answer(ev->tid,200,options);
1813         }else if (strncmp(ev->request->sip_method, "REFER", 5) == 0){
1814                 ms_message("Receiving REFER request !");
1815                 if (comes_from_local_if(ev->request)) {
1816                         process_refer(sal,NULL,ev);
1817                 }else ms_warning("Ignored REFER not coming from this local loopback interface.");
1818         }else if (strncmp(ev->request->sip_method, "UPDATE", 6) == 0){
1819                 inc_update(sal,ev);
1820         }else {
1821                 char *tmp=NULL;
1822                 size_t msglen=0;
1823                 osip_message_to_str(ev->request,&tmp,&msglen);
1824                 if (tmp){
1825                         ms_message("Unsupported request received:\n%s",tmp);
1826                         osip_free(tmp);
1827                 }
1828                 /*answer with a 501 Not implemented*/
1829                 eXosip_message_send_answer(ev->tid,501,NULL);
1830         }
1831 }
1832
1833 static void masquerade_via(osip_message_t *msg, const char *ip, const char *port){
1834         osip_via_t *via=NULL;
1835         osip_message_get_via(msg,0,&via);
1836         if (via){
1837                 osip_free(via->port);
1838                 via->port=osip_strdup(port);
1839                 osip_free(via->host);
1840                 via->host=osip_strdup(ip);
1841         }
1842 }
1843
1844
1845 static bool_t fix_message_contact(SalOp *op, osip_message_t *request,osip_message_t *last_answer, bool_t expire_last_contact) {
1846         osip_contact_t *ctt=NULL;
1847         const char *received;
1848         int rport;
1849         SalTransport transport;
1850         char port[20];
1851
1852         if (extract_received_rport(last_answer,&received,&rport,&transport)==-1) return FALSE;
1853         osip_message_get_contact(request,0,&ctt);
1854         if (ctt == NULL) {
1855                 ms_warning("fix_message_contact(): no contact to update");
1856                 return FALSE;
1857         }
1858         if (expire_last_contact){
1859                 osip_contact_t *oldct=NULL,*prevct;
1860                 osip_generic_param_t *param=NULL;
1861                 osip_contact_clone(ctt,&oldct);
1862                 while ((prevct=(osip_contact_t*)osip_list_get(&request->contacts,1))!=NULL){
1863                         osip_contact_free(prevct);
1864                         osip_list_remove(&request->contacts,1);
1865                 }
1866                 osip_list_add(&request->contacts,oldct,1);
1867                 osip_contact_param_get_byname(oldct,"expires",&param);
1868                 if (param){
1869                         if (param->gvalue) osip_free(param->gvalue);
1870                         param->gvalue=osip_strdup("0");
1871                 }else{
1872                         osip_contact_param_add(oldct,osip_strdup("expires"),osip_strdup("0"));
1873                 }
1874         }
1875         if (ctt->url->host!=NULL){
1876                 osip_free(ctt->url->host);
1877         }
1878         ctt->url->host=osip_strdup(received);
1879         if (ctt->url->port!=NULL){
1880                 osip_free(ctt->url->port);
1881         }
1882         snprintf(port,sizeof(port),"%i",rport);
1883         ctt->url->port=osip_strdup(port);
1884         if (op->masquerade_via) masquerade_via(request,received,port);
1885
1886         if (transport != SalTransportUDP) {
1887                 sal_address_set_param((SalAddress *)ctt, "transport", sal_transport_to_string(transport)); 
1888         }
1889         return TRUE;    
1890 }
1891
1892 static bool_t register_again_with_updated_contact(SalOp *op, osip_message_t *orig_request, osip_message_t *last_answer){
1893         osip_contact_t *ctt=NULL;
1894         SalAddress* ori_contact_address=NULL;
1895         const char *received;
1896         int rport;
1897         SalTransport transport;
1898         char* tmp;
1899         osip_message_t *msg=NULL;
1900         Sal* sal=op->base.root;
1901         int i=0;
1902         bool_t found_valid_contact=FALSE;
1903         bool_t from_request=FALSE;
1904
1905         if (sal->double_reg==FALSE ) return FALSE; 
1906
1907         if (extract_received_rport(last_answer,&received,&rport,&transport)==-1) return FALSE;
1908         do{
1909                 ctt=NULL;
1910                 osip_message_get_contact(last_answer,i,&ctt);
1911                 if (!from_request && ctt==NULL) {
1912                         osip_message_get_contact(orig_request,0,&ctt);
1913                         from_request=TRUE;
1914                 }
1915                 if (ctt){
1916                         osip_contact_to_str(ctt,&tmp);
1917                         ori_contact_address = sal_address_new(tmp);
1918         
1919                         /*check if contact is up to date*/
1920                         if (strcmp(sal_address_get_domain(ori_contact_address),received) ==0 
1921                                 && sal_address_get_port_int(ori_contact_address) == rport
1922                         && sal_address_get_transport(ori_contact_address) == transport) {
1923                                 if (!from_request){
1924                                         ms_message("Register response has up to date contact, doing nothing.");
1925                                 }else {
1926                                         ms_warning("Register response does not have up to date contact, but last request had."
1927                                                 "Stupid registrar detected, giving up.");
1928                                 }
1929                                 found_valid_contact=TRUE;
1930                         }
1931                         osip_free(tmp);
1932                         sal_address_destroy(ori_contact_address);
1933                 }else break;
1934                 i++;
1935         }while(!found_valid_contact);
1936         if (!found_valid_contact)
1937                 ms_message("Contact do not match, resending register.");
1938         else return FALSE;
1939
1940         eXosip_lock();
1941         eXosip_register_build_register(op->rid,op->expires,&msg);
1942         if (msg==NULL){
1943             eXosip_unlock();
1944             ms_warning("Fail to create a contact updated register.");
1945             return FALSE;
1946         }
1947         if (fix_message_contact(op,msg,last_answer,op->base.root->expire_old_contact)) {
1948                 eXosip_register_send_register(op->rid,msg);
1949                 eXosip_unlock();  
1950                 ms_message("Resending new register with updated contact");
1951                 update_contact_from_response(op,last_answer);
1952                 return TRUE;
1953         } else {
1954             ms_warning("Fail to send updated register.");
1955             eXosip_unlock();
1956             return FALSE;
1957         }
1958         eXosip_unlock();
1959         return FALSE;
1960 }
1961
1962 static void registration_success(Sal *sal, eXosip_event_t *ev){
1963         SalOp *op=sal_find_register(sal,ev->rid);
1964         osip_header_t *h=NULL;
1965         bool_t registered;
1966         if (op==NULL){
1967                 ms_error("Receiving register response for unknown operation");
1968                 return;
1969         }
1970         osip_message_get_expires(ev->request,0,&h);
1971         if (h!=NULL && atoi(h->hvalue)!=0){
1972                 registered=TRUE;
1973                 if (!register_again_with_updated_contact(op,ev->request,ev->response)){
1974                         sal->callbacks.register_success(op,registered);
1975                 }
1976         }else {
1977                 sal->callbacks.register_success(op,FALSE);
1978         }
1979 }
1980
1981 static bool_t registration_failure(Sal *sal, eXosip_event_t *ev){
1982         int status_code=0;
1983         const char *reason=NULL;
1984         SalOp *op=sal_find_register(sal,ev->rid);
1985         SalReason sr=SalReasonUnknown;
1986         SalError se=SalErrorUnknown;
1987         
1988         if (op==NULL){
1989                 ms_error("Receiving register failure for unknown operation");
1990                 return TRUE;
1991         }
1992         if (ev->response){
1993                 status_code=osip_message_get_status_code(ev->response);
1994                 reason=osip_message_get_reason_phrase(ev->response);
1995         }
1996         switch(status_code){
1997                 case 401:
1998                 case 407:
1999                         return process_authentication(sal,ev);
2000                         break;
2001                 case 423: /*interval too brief*/
2002                         {/*retry with greater interval */
2003                                 osip_header_t *h=NULL;
2004                                 osip_message_t *msg=NULL;
2005                                 osip_message_header_get_byname(ev->response,"min-expires",0,&h);
2006                                 if (h && h->hvalue && h->hvalue[0]!='\0'){
2007                                         int val=atoi(h->hvalue);
2008                                         if (val>op->expires)
2009                                                 op->expires=val;
2010                                 }else op->expires*=2;
2011                                 eXosip_lock();
2012                                 eXosip_register_build_register(op->rid,op->expires,&msg);
2013                                 eXosip_register_send_register(op->rid,msg);
2014                                 eXosip_unlock();
2015                         }
2016                 break;
2017                 case 606: /*Not acceptable, workaround for proxies that don't like private addresses
2018                                  in vias, such as ekiga.net 
2019                                  On the opposite, freephonie.net bugs when via are masqueraded.
2020                                  */
2021                         op->masquerade_via=TRUE;
2022                 default:
2023                         /* if contact is up to date, process the failure, otherwise resend a new register with
2024                                 updated contact first, just in case the faillure is due to incorrect contact */
2025                         if (ev->response && register_again_with_updated_contact(op,ev->request,ev->response))
2026                                 return TRUE; /*we are retrying with an updated contact*/
2027                         if (status_code==403){
2028                                 se=SalErrorFailure;
2029                                 sr=SalReasonForbidden;
2030                         }else if (status_code==0){
2031                                 se=SalErrorNoResponse;
2032                         }
2033                         sal->callbacks.register_failure(op,se,sr,reason);
2034         }
2035         return TRUE;
2036 }
2037
2038 static void other_request_reply(Sal *sal,eXosip_event_t *ev){
2039         SalOp *op=find_op(sal,ev);
2040         if (op==NULL){
2041                 ms_warning("other_request_reply(): Receiving response to unknown request.");
2042                 return;
2043         }
2044         if (ev->response){
2045                 ms_message("Processing reponse status [%i] for method [%s]",ev->response->status_code,osip_message_get_method(ev->request));
2046                 update_contact_from_response(op,ev->response);
2047                 if (ev->request && strcmp(osip_message_get_method(ev->request),"OPTIONS")==0)
2048                         sal->callbacks.ping_reply(op);
2049         }
2050         if (ev->request && strcmp(osip_message_get_method(ev->request),"MESSAGE")==0) {
2051                 /*out of call message acknolegment*/
2052                 SalTextDeliveryStatus status=SalTextDeliveryFailed;
2053                 if (ev->response){
2054                         if (ev->response->status_code<200){
2055                                 status=SalTextDeliveryInProgress;
2056                         }else if (ev->response->status_code<300 && ev->response->status_code>=200){
2057                                 status=SalTextDeliveryDone;
2058                         }
2059                 }
2060                 sal->callbacks.text_delivery_update(op,status);
2061         }
2062 }
2063
2064 static void process_in_call_reply(Sal *sal, eXosip_event_t *ev){
2065         SalOp *op=find_op(sal,ev);
2066         if (ev->response){
2067                 if (ev->request && strcmp(osip_message_get_method(ev->request),"NOTIFY")==0){
2068                         if (op->sipfrag_pending){
2069                                 send_notify_for_refer(op->did,op->sipfrag_pending);
2070                                 op->sipfrag_pending=NULL;
2071                         }
2072                 }
2073         }
2074 }
2075
2076 static bool_t process_event(Sal *sal, eXosip_event_t *ev){
2077         ms_message("linphone process event get a message %d\n",ev->type);
2078         switch(ev->type){
2079                 case EXOSIP_CALL_ANSWERED:
2080                         ms_message("CALL_ANSWERED\n");
2081                         call_accepted(sal,ev);
2082                         authentication_ok(sal,ev);
2083                         break;
2084                 case EXOSIP_CALL_CLOSED:
2085                 case EXOSIP_CALL_CANCELLED:
2086                         ms_message("CALL_CLOSED or CANCELLED\n");
2087                         call_terminated(sal,ev);
2088                         break;
2089                 case EXOSIP_CALL_TIMEOUT:
2090                 case EXOSIP_CALL_NOANSWER:
2091                         ms_message("CALL_TIMEOUT or NOANSWER\n");
2092                         return call_failure(sal,ev);
2093                         break;
2094                 case EXOSIP_CALL_REQUESTFAILURE:
2095                 case EXOSIP_CALL_GLOBALFAILURE:
2096                 case EXOSIP_CALL_SERVERFAILURE:
2097                         ms_message("CALL_REQUESTFAILURE or GLOBALFAILURE or SERVERFAILURE\n");
2098                         return call_failure(sal,ev);
2099                         break;
2100                 case EXOSIP_CALL_RELEASED:
2101                         ms_message("CALL_RELEASED\n");
2102                         call_released(sal, ev);
2103                         break;
2104                 case EXOSIP_CALL_INVITE:
2105                         ms_message("CALL_NEW\n");
2106                         inc_new_call(sal,ev);
2107                         break;
2108                 case EXOSIP_CALL_REINVITE:
2109                         handle_reinvite(sal,ev);
2110                         break;
2111                 case EXOSIP_CALL_ACK:
2112                         ms_message("CALL_ACK");
2113                         handle_ack(sal,ev);
2114                         break;
2115                 case EXOSIP_CALL_REDIRECTED:
2116                         ms_message("CALL_REDIRECTED");
2117                         eXosip_default_action(ev);
2118                         break;
2119                 case EXOSIP_CALL_PROCEEDING:
2120                         ms_message("CALL_PROCEEDING");
2121                         call_proceeding(sal,ev);
2122                         break;
2123                 case EXOSIP_CALL_RINGING:
2124                         ms_message("CALL_RINGING");
2125                         call_ringing(sal,ev);
2126                         authentication_ok(sal,ev);
2127                         break;
2128                 case EXOSIP_CALL_MESSAGE_NEW:
2129                         ms_message("EXOSIP_CALL_MESSAGE_NEW");
2130                         call_message_new(sal,ev);
2131                         break;
2132                 case EXOSIP_CALL_MESSAGE_REQUESTFAILURE:
2133                         if (ev->response &&
2134                                 (ev->response->status_code==407 || ev->response->status_code==401)){
2135                                  return process_authentication(sal,ev);
2136                         }
2137                         break;
2138                 case EXOSIP_CALL_MESSAGE_ANSWERED:
2139                         ms_message("EXOSIP_CALL_MESSAGE_ANSWERED ");
2140                         process_in_call_reply(sal,ev);
2141                 break;
2142                 case EXOSIP_IN_SUBSCRIPTION_NEW:
2143                         ms_message("CALL_IN_SUBSCRIPTION_NEW ");
2144                         sal_exosip_subscription_recv(sal,ev);
2145                         break;
2146                 case EXOSIP_IN_SUBSCRIPTION_RELEASED:
2147                         ms_message("CALL_SUBSCRIPTION_NEW ");
2148                         sal_exosip_in_subscription_closed(sal,ev);
2149                         break;
2150                 case EXOSIP_SUBSCRIPTION_UPDATE:
2151                         ms_message("CALL_SUBSCRIPTION_UPDATE");
2152                         break;
2153                 case EXOSIP_SUBSCRIPTION_NOTIFY:
2154                         ms_message("CALL_SUBSCRIPTION_NOTIFY");
2155                         sal_exosip_notify_recv(sal,ev);
2156                         break;
2157                 case EXOSIP_SUBSCRIPTION_ANSWERED:
2158                         ms_message("EXOSIP_SUBSCRIPTION_ANSWERED, ev->sid=%i, ev->did=%i\n",ev->sid,ev->did);
2159                         sal_exosip_subscription_answered(sal,ev);
2160                         break;
2161                 case EXOSIP_SUBSCRIPTION_CLOSED:
2162                         ms_message("EXOSIP_SUBSCRIPTION_CLOSED\n");
2163                         sal_exosip_subscription_closed(sal,ev);
2164                         break;
2165                 case EXOSIP_SUBSCRIPTION_REQUESTFAILURE:   /**< announce a request failure      */
2166                         if (ev->response && (ev->response->status_code == 407 || ev->response->status_code == 401)){
2167                                 return process_authentication(sal,ev);
2168                         }
2169                 case EXOSIP_SUBSCRIPTION_SERVERFAILURE:
2170                 case EXOSIP_SUBSCRIPTION_GLOBALFAILURE:
2171                         sal_exosip_subscription_closed(sal,ev);
2172                         break;
2173                 case EXOSIP_REGISTRATION_FAILURE:
2174                         ms_message("REGISTRATION_FAILURE\n");
2175                         return registration_failure(sal,ev);
2176                         break;
2177                 case EXOSIP_REGISTRATION_SUCCESS:
2178                         authentication_ok(sal,ev);
2179                         registration_success(sal,ev);
2180                         break;
2181                 case EXOSIP_MESSAGE_NEW:
2182                         other_request(sal,ev);
2183                         break;
2184                 case EXOSIP_MESSAGE_PROCEEDING:
2185                 case EXOSIP_MESSAGE_ANSWERED:
2186                 case EXOSIP_MESSAGE_REDIRECTED:
2187                 case EXOSIP_MESSAGE_SERVERFAILURE:
2188                 case EXOSIP_MESSAGE_GLOBALFAILURE:
2189                         other_request_reply(sal,ev);
2190                         break;
2191                 case EXOSIP_MESSAGE_REQUESTFAILURE:
2192                 case EXOSIP_NOTIFICATION_REQUESTFAILURE:
2193                         if (ev->response) {
2194                                 switch (ev->response->status_code) {
2195                                         case 407:
2196                                         case 401:
2197                                                 return process_authentication(sal,ev);
2198                                         case 412: {
2199                                                 eXosip_automatic_action ();
2200                                                 return 1;
2201                                         }
2202                                 }
2203                         }
2204                         other_request_reply(sal,ev);
2205                         break;
2206                 default:
2207                         ms_message("Unhandled exosip event ! %i",ev->type);
2208                         break;
2209         }
2210         return TRUE;
2211 }
2212
2213 int sal_iterate(Sal *sal){
2214         eXosip_event_t *ev;
2215         while((ev=eXosip_event_wait(0,0))!=NULL){
2216                 if (process_event(sal,ev))
2217                         eXosip_event_free(ev);
2218         }
2219 #ifdef HAVE_EXOSIP_TRYLOCK
2220         if (eXosip_trylock()==0){
2221                 eXosip_automatic_refresh();
2222                 eXosip_unlock();
2223         }else{
2224                 ms_warning("eXosip_trylock busy.");
2225         }
2226 #else
2227         eXosip_lock();
2228         eXosip_automatic_refresh();
2229         eXosip_unlock();
2230 #endif
2231         return 0;
2232 }
2233
2234 static void register_set_contact(osip_message_t *msg, const char *contact){
2235         osip_uri_param_t *param = NULL;
2236         osip_contact_t *ct=NULL;
2237         char *line=NULL;
2238         /*we get the line parameter choosed by exosip, and add it to our own contact*/
2239         osip_message_get_contact(msg,0,&ct);
2240         if (ct!=NULL){
2241                 osip_uri_uparam_get_byname(ct->url, "line", &param);
2242                 if (param && param->gvalue)
2243                         line=osip_strdup(param->gvalue);
2244         }
2245         _osip_list_set_empty(&msg->contacts,(void (*)(void*))osip_contact_free);
2246         osip_message_set_contact(msg,contact);
2247         osip_message_get_contact(msg,0,&ct);
2248         osip_uri_uparam_add(ct->url,osip_strdup("line"),line);
2249 }
2250
2251 static void sal_register_add_route(osip_message_t *msg, const char *proxy){
2252         osip_route_t *route;
2253
2254         osip_list_special_free(&msg->routes,(void (*)(void*))osip_route_free);
2255         
2256         osip_route_init(&route);
2257         if (osip_route_parse(route,proxy)==0){
2258                 osip_uri_param_t *lr_param = NULL;
2259                 osip_uri_uparam_get_byname(route->url, "lr", &lr_param);
2260                 if (lr_param == NULL){
2261                         osip_uri_uparam_add(route->url,osip_strdup("lr"),NULL);
2262                 }
2263                 osip_list_add(&msg->routes,route,0);
2264                 return;
2265         }
2266         osip_route_free(route);
2267 }
2268
2269
2270 int sal_register(SalOp *h, const char *proxy, const char *from, int expires){
2271         osip_message_t *msg;
2272         const char *contact=sal_op_get_contact(h);
2273
2274         sal_op_set_route(h,proxy);
2275         if (h->rid==-1){
2276                 SalAddress *from_parsed=sal_address_new(from);
2277                 char domain[256];
2278                 char *uri, *domain_ptr = NULL;
2279                 if (from_parsed==NULL) {
2280                         ms_warning("sal_register() bad from %s",from);
2281                         return -1;
2282                 }
2283                 /* Get domain using sal_address_as_string_uri_only() and stripping the username part instead of
2284                    using sal_address_get_domain() because to have a properly formatted domain with IPv6 proxy addresses. */
2285                 uri = sal_address_as_string_uri_only(from_parsed);
2286                 if (uri) domain_ptr = strchr(uri, '@');
2287                 if (domain_ptr) {
2288                         snprintf(domain,sizeof(domain),"sip:%s",domain_ptr+1);
2289                 } else {
2290                         snprintf(domain,sizeof(domain),"sip:%s",sal_address_get_domain(from_parsed));
2291                 }
2292                 if (uri) ms_free(uri);
2293                 sal_address_destroy(from_parsed);
2294                 eXosip_lock();
2295                 h->rid=eXosip_register_build_initial_register(from,domain,NULL,expires,&msg);
2296                 if (msg){
2297                         if (contact) register_set_contact(msg,contact);
2298                         sal_register_add_route(msg,proxy);
2299                         sal_add_register(h->base.root,h);
2300                 }else{
2301                         ms_error("Could not build initial register.");
2302                         eXosip_unlock();
2303                         return -1;
2304                 }
2305         }else{
2306                 eXosip_lock();
2307                 eXosip_register_build_register(h->rid,expires,&msg);
2308                 sal_register_add_route(msg,proxy);
2309         }
2310         if (msg){
2311                 eXosip_register_send_register(h->rid,msg);
2312         }
2313         eXosip_unlock();
2314         h->expires=expires;
2315         return (msg != NULL) ? 0 : -1;
2316 }
2317
2318 int sal_register_refresh(SalOp *op, int expires){
2319         osip_message_t *msg=NULL;
2320         const char *contact=sal_op_get_contact(op);
2321         
2322         if (op->rid==-1){
2323                 ms_error("Unexistant registration context, not possible to refresh.");
2324                 return -1;
2325         }
2326 #ifdef HAVE_EXOSIP_TRYLOCK
2327         {
2328                 int tries=0;
2329                 /*iOS hack: in the keep alive handler, we have no more than 10 seconds to refresh registers, otherwise the application is suspended forever.
2330                 * In order to prevent this case that can occur when the exosip thread is busy with DNS while network isn't in a good shape, we try to take
2331                 * the exosip lock in a non blocking way, and give up if it takes too long*/
2332                 while (eXosip_trylock()!=0){
2333                         ms_usleep(100000);
2334                         if (tries>30) {/*after 3 seconds, give up*/
2335                                 ms_warning("Could not obtain exosip lock in a reasonable time, giving up.");
2336                                 return -1;
2337                         }
2338                 }
2339         }
2340 #else
2341         eXosip_lock();
2342 #endif
2343         eXosip_register_build_register(op->rid,expires,&msg);
2344         if (msg!=NULL){
2345                 if (contact) register_set_contact(msg,contact);
2346                 sal_register_add_route(msg,sal_op_get_route(op));
2347                 eXosip_register_send_register(op->rid,msg);
2348         }else ms_error("Could not build REGISTER refresh message.");
2349         eXosip_unlock();
2350         return (msg != NULL) ? 0 : -1;
2351 }
2352
2353
2354 int sal_unregister(SalOp *h){
2355         osip_message_t *msg=NULL;
2356         eXosip_lock();
2357         eXosip_register_build_register(h->rid,0,&msg);
2358         if (msg) eXosip_register_send_register(h->rid,msg);
2359         else ms_warning("Could not build unREGISTER !");
2360         eXosip_unlock();
2361         return 0;
2362 }
2363
2364 SalAddress * sal_address_new(const char *uri){
2365         osip_from_t *from;
2366         osip_from_init(&from);
2367
2368         // Remove front spaces
2369         while (uri[0]==' ') {
2370                 uri++;
2371         }
2372                 
2373         if (osip_from_parse(from,uri)!=0){
2374                 osip_from_free(from);
2375                 return NULL;
2376         }
2377         if (from->displayname!=NULL && from->displayname[0]=='"'){
2378                 char *unquoted=osip_strdup_without_quote(from->displayname);
2379                 osip_free(from->displayname);
2380                 from->displayname=unquoted;
2381         }
2382         return (SalAddress*)from;
2383 }
2384
2385 SalAddress * sal_address_clone(const SalAddress *addr){
2386         osip_from_t *ret=NULL;
2387         osip_from_clone((osip_from_t*)addr,&ret);
2388         return (SalAddress*)ret;
2389 }
2390
2391 #define null_if_empty(s) (((s)!=NULL && (s)[0]!='\0') ? (s) : NULL )
2392
2393 const char *sal_address_get_scheme(const SalAddress *addr){
2394         const osip_from_t *u=(const osip_from_t*)addr;
2395         return null_if_empty(u->url->scheme);
2396 }
2397
2398 const char *sal_address_get_display_name(const SalAddress* addr){
2399         const osip_from_t *u=(const osip_from_t*)addr;
2400         return null_if_empty(u->displayname);
2401 }
2402
2403 const char *sal_address_get_username(const SalAddress *addr){
2404         const osip_from_t *u=(const osip_from_t*)addr;
2405         return null_if_empty(u->url->username);
2406 }
2407
2408 const char *sal_address_get_domain(const SalAddress *addr){
2409         const osip_from_t *u=(const osip_from_t*)addr;
2410         return null_if_empty(u->url->host);
2411 }
2412
2413 void sal_address_set_display_name(SalAddress *addr, const char *display_name){
2414         osip_from_t *u=(osip_from_t*)addr;
2415         if (u->displayname!=NULL){
2416                 osip_free(u->displayname);
2417                 u->displayname=NULL;
2418         }
2419         if (display_name!=NULL && display_name[0]!='\0'){
2420                 u->displayname=osip_strdup(display_name);
2421         }
2422 }
2423
2424 void sal_address_set_username(SalAddress *addr, const char *username){
2425         osip_from_t *uri=(osip_from_t*)addr;
2426         if (uri->url->username!=NULL){
2427                 osip_free(uri->url->username);
2428                 uri->url->username=NULL;
2429         }
2430         if (username)
2431                 uri->url->username=osip_strdup(username);
2432 }
2433
2434 void sal_address_set_domain(SalAddress *addr, const char *host){
2435         osip_from_t *uri=(osip_from_t*)addr;
2436         if (uri->url->host!=NULL){
2437                 osip_free(uri->url->host);
2438                 uri->url->host=NULL;
2439         }
2440         if (host)
2441                 uri->url->host=osip_strdup(host);
2442 }
2443
2444 void sal_address_set_port(SalAddress *addr, const char *port){
2445         osip_from_t *uri=(osip_from_t*)addr;
2446         if (uri->url->port!=NULL){
2447                 osip_free(uri->url->port);
2448                 uri->url->port=NULL;
2449         }
2450         if (port)
2451                 uri->url->port=osip_strdup(port);
2452 }
2453
2454 void sal_address_set_port_int(SalAddress *uri, int port){
2455         char tmp[12];
2456         if (port==5060){
2457                 /*this is the default, special case to leave the port field blank*/
2458                 sal_address_set_port(uri,NULL);
2459                 return;
2460         }
2461         snprintf(tmp,sizeof(tmp),"%i",port);
2462         sal_address_set_port(uri,tmp);
2463 }
2464
2465 void sal_address_clean(SalAddress *addr){
2466         osip_generic_param_freelist(& ((osip_from_t*)addr)->gen_params);
2467         osip_uri_param_freelist(& ((osip_from_t*)addr)->url->url_params);
2468 }
2469
2470 char *sal_address_as_string(const SalAddress *u){
2471         char *tmp,*ret;
2472         osip_from_t *from=(osip_from_t *)u;
2473         char *old_displayname=NULL;
2474         /* hack to force use of quotes around the displayname*/
2475         if (from->displayname!=NULL
2476             && from->displayname[0]!='"'){
2477                 old_displayname=from->displayname;
2478                 from->displayname=osip_enquote(from->displayname);
2479         }
2480         osip_from_to_str(from,&tmp);
2481         if (old_displayname!=NULL){
2482                 ms_free(from->displayname);
2483                 from->displayname=old_displayname;
2484         }
2485         ret=ms_strdup(tmp);
2486         osip_free(tmp);
2487         return ret;
2488 }
2489
2490 char *sal_address_as_string_uri_only(const SalAddress *u){
2491         char *tmp=NULL,*ret;
2492         osip_uri_to_str(((osip_from_t*)u)->url,&tmp);
2493         ret=ms_strdup(tmp);
2494         osip_free(tmp);
2495         return ret;
2496 }
2497 void sal_address_set_param(SalAddress *u,const char* name,const char* value) {
2498         osip_uri_param_t *param=NULL;
2499     osip_uri_uparam_get_byname(((osip_from_t*)u)->url,(char*)name,&param);
2500     if (param == NULL){
2501         osip_uri_uparam_add     (((osip_from_t*)u)->url,ms_strdup(name),value ? ms_strdup(value) : NULL);
2502     } else {
2503         osip_free(param->gvalue);
2504         param->gvalue=value ? osip_strdup(value) : NULL;
2505     }
2506     
2507 }
2508
2509 void sal_address_destroy(SalAddress *u){
2510         osip_from_free((osip_from_t*)u);
2511 }
2512
2513 void sal_use_tcp_tls_keepalive(Sal *ctx, bool_t enabled) {
2514         ctx->tcp_tls_keepalive = enabled;
2515 }
2516
2517 void sal_set_keepalive_period(Sal *ctx,unsigned int value) {
2518         switch (ctx->transport) {
2519                 case SalTransportUDP:
2520                         ctx->keepalive_period = value;
2521                         break;
2522                 case SalTransportTCP:
2523                 case SalTransportTLS:
2524                         if (ctx->tcp_tls_keepalive) ctx->keepalive_period = value;
2525                         else ctx->keepalive_period = -1;
2526                         break;
2527                 default:
2528                         break;
2529         }
2530         eXosip_set_option (EXOSIP_OPT_UDP_KEEP_ALIVE, &ctx->keepalive_period);
2531 }
2532 unsigned int sal_get_keepalive_period(Sal *ctx) {
2533         return ctx->keepalive_period;
2534 }
2535
2536 const char * sal_address_get_port(const SalAddress *addr) {
2537         const osip_from_t *u=(const osip_from_t*)addr;
2538         return null_if_empty(u->url->port);
2539 }
2540
2541 int sal_address_get_port_int(const SalAddress *uri) {
2542         const char* port = sal_address_get_port(uri);
2543         if (port != NULL) {
2544                 return atoi(port);
2545         } else {
2546                 return 5060;
2547         }
2548 }
2549 SalTransport sal_address_get_transport(const SalAddress* addr) {
2550     const osip_from_t *u=(const osip_from_t*)addr;
2551     osip_uri_param_t *transport_param=NULL;
2552     osip_uri_uparam_get_byname(u->url,"transport",&transport_param);
2553     if (transport_param == NULL){
2554         return SalTransportUDP;
2555     }  else {
2556         return sal_transport_parse(transport_param->gvalue);
2557     }
2558 }
2559 void sal_address_set_transport(SalAddress* addr,SalTransport transport) {
2560     sal_address_set_param(addr, "transport", sal_transport_to_string(transport));
2561 }
2562
2563 /* sends a reinvite. Local media description may have changed by application since call establishment*/
2564 int sal_call_update(SalOp *h, const char *subject){
2565         int err=0;
2566         osip_message_t *reinvite=NULL;
2567
2568         eXosip_lock();
2569         if(eXosip_call_build_request(h->did,"INVITE",&reinvite) != 0 || reinvite==NULL){
2570                 eXosip_unlock();
2571                 return -1;
2572         }
2573         eXosip_unlock();
2574         osip_message_set_subject(reinvite,subject);
2575         osip_message_set_allow(reinvite, "INVITE, ACK, CANCEL, OPTIONS, BYE, REFER, NOTIFY, MESSAGE, SUBSCRIBE, INFO");
2576         if (h->base.contact){
2577                 _osip_list_set_empty(&reinvite->contacts,(void (*)(void*))osip_contact_free);
2578                 osip_message_set_contact(reinvite,h->base.contact);
2579         }
2580         if (h->base.root->session_expires!=0){
2581                 osip_message_set_header(reinvite, "Session-expires", "200");
2582                 osip_message_set_supported(reinvite, "timer");
2583         }
2584         if (h->base.local_media){
2585                 h->sdp_offering=TRUE;
2586                 set_sdp_from_desc(reinvite,h->base.local_media);
2587         }else h->sdp_offering=FALSE;
2588         eXosip_lock();
2589         err = eXosip_call_send_request(h->did, reinvite);
2590         eXosip_unlock();
2591         return err;
2592 }
2593 void sal_reuse_authorization(Sal *ctx, bool_t value) {
2594         ctx->reuse_authorization=value;
2595 }