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