~noskcaj/ubuntu/saucy/sflphone/merge-1.2.3-2

« back to all changes in this revision

Viewing changes to daemon/src/sip/sipvoiplink.cpp

  • Committer: Package Import Robot
  • Author(s): Francois Marier
  • Date: 2012-02-18 21:47:09 UTC
  • mfrom: (1.1.6)
  • Revision ID: package-import@ubuntu.com-20120218214709-6362d71gqdsdkrj5
Tags: 1.0.2-1
* New upstream release
  - remove logging patch (applied upstream)
  - update s390 patch since it was partially applied upstream
* Include the Evolution plugin as a separate binary package

* Fix compilation issues on SH4 (closes: #658987)
* Merge Ubuntu's binutils-gold linking fix

Show diffs side-by-side

added added

removed removed

Lines of Context:
94
94
/**
95
95
 * Helper function to parser header from incoming sip messages
96
96
 */
97
 
std::string fetchHeaderValue(pjsip_msg *msg, std::string field);
 
97
std::string fetchHeaderValue(pjsip_msg *msg, const std::string &field);
98
98
 
99
99
static pj_caching_pool pool_cache, *cp_ = &pool_cache;
100
100
static pj_pool_t *pool_;
102
102
static pjsip_module mod_ua_;
103
103
static pj_thread_t *thread;
104
104
 
105
 
static void sdp_media_update_cb(pjsip_inv_session *inv, pj_status_t status UNUSED);
106
 
static void sdp_request_offer_cb(pjsip_inv_session *inv, const pjmedia_sdp_session *offer);
107
 
static void sdp_create_offer_cb(pjsip_inv_session *inv, pjmedia_sdp_session **p_offer);
108
 
static void invite_session_state_changed_cb(pjsip_inv_session *inv, pjsip_event *e);
109
 
static void outgoing_request_forked_cb(pjsip_inv_session *inv, pjsip_event *e);
110
 
static void transaction_state_changed_cb(pjsip_inv_session *inv, pjsip_transaction *tsx, pjsip_event *e);
111
 
static void registration_cb(pjsip_regc_cbparam *param);
112
 
static pj_bool_t transaction_request_cb(pjsip_rx_data *rdata);
113
 
static pj_bool_t transaction_response_cb(pjsip_rx_data *rdata UNUSED) ;
 
105
void sdp_media_update_cb(pjsip_inv_session *inv, pj_status_t status UNUSED);
 
106
void sdp_request_offer_cb(pjsip_inv_session *inv, const pjmedia_sdp_session *offer);
 
107
void sdp_create_offer_cb(pjsip_inv_session *inv, pjmedia_sdp_session **p_offer);
 
108
void invite_session_state_changed_cb(pjsip_inv_session *inv, pjsip_event *e);
 
109
void outgoing_request_forked_cb(pjsip_inv_session *inv, pjsip_event *e);
 
110
void transaction_state_changed_cb(pjsip_inv_session *inv, pjsip_transaction *tsx, pjsip_event *e);
 
111
void registration_cb(pjsip_regc_cbparam *param);
 
112
pj_bool_t transaction_request_cb(pjsip_rx_data *rdata);
 
113
pj_bool_t transaction_response_cb(pjsip_rx_data *rdata UNUSED) ;
114
114
 
115
 
static void transfer_client_cb(pjsip_evsub *sub, pjsip_event *event);
 
115
void transfer_client_cb(pjsip_evsub *sub, pjsip_event *event);
116
116
 
117
117
/**
118
118
 * Send a reINVITE inside an active dialog to modify its state
163
163
    return route_set;
164
164
}
165
165
 
 
166
void handleIncomingOptions(pjsip_rx_data *rdata)
 
167
{
 
168
    pjsip_tx_data *tdata;
 
169
 
 
170
    if (pjsip_endpt_create_response(endpt_, rdata, PJSIP_SC_OK, NULL, &tdata) != PJ_SUCCESS)
 
171
        return;
 
172
 
 
173
#define ADD_HDR(hdr) do { \
 
174
    const pjsip_hdr *cap_hdr = hdr; \
 
175
    if (cap_hdr) \
 
176
    pjsip_msg_add_hdr (tdata->msg, (pjsip_hdr*) pjsip_hdr_clone (tdata->pool, cap_hdr)); \
 
177
} while(0)
 
178
#define ADD_CAP(cap) ADD_HDR(pjsip_endpt_get_capability(endpt_, cap, NULL));
 
179
 
 
180
    ADD_CAP(PJSIP_H_ALLOW);
 
181
    ADD_CAP(PJSIP_H_ACCEPT);
 
182
    ADD_CAP(PJSIP_H_SUPPORTED);
 
183
    ADD_HDR(pjsip_evsub_get_allow_events_hdr(NULL));
 
184
 
 
185
    pjsip_response_addr res_addr;
 
186
    pjsip_get_response_addr(tdata->pool, rdata, &res_addr);
 
187
 
 
188
    if (pjsip_endpt_send_response(endpt_, &res_addr, tdata, NULL, NULL) != PJ_SUCCESS)
 
189
        pjsip_tx_data_dec_ref(tdata);
 
190
}
 
191
 
 
192
pj_bool_t transaction_response_cb(pjsip_rx_data *rdata)
 
193
{
 
194
    pjsip_dialog *dlg = pjsip_rdata_get_dlg(rdata);
 
195
 
 
196
    if (!dlg)
 
197
        return PJ_SUCCESS;
 
198
 
 
199
    pjsip_transaction *tsx = pjsip_rdata_get_tsx(rdata);
 
200
 
 
201
    if (!tsx or tsx->method.id != PJSIP_INVITE_METHOD)
 
202
        return PJ_SUCCESS;
 
203
 
 
204
    if (tsx->status_code / 100 == 2) {
 
205
        /**
 
206
         * Send an ACK message inside a transaction. PJSIP send automatically, non-2xx ACK response.
 
207
         * ACK for a 2xx response must be send using this method.
 
208
         */
 
209
        pjsip_tx_data *tdata;
 
210
        pjsip_dlg_create_request(dlg, &pjsip_ack_method, rdata->msg_info.cseq->cseq, &tdata);
 
211
        pjsip_dlg_send_request(dlg, tdata, -1, NULL);
 
212
    }
 
213
 
 
214
    return PJ_SUCCESS;
 
215
}
 
216
 
 
217
std::string parseDisplayName(const char * buffer)
 
218
{
 
219
    const char* from_header = strstr(buffer, "From: ");
 
220
 
 
221
    if (!from_header)
 
222
        return "";
 
223
 
 
224
    std::string temp(from_header);
 
225
    size_t begin_displayName = temp.find("\"") + 1;
 
226
    size_t end_displayName = temp.rfind("\"");
 
227
    std::string displayName(temp.substr(begin_displayName, end_displayName - begin_displayName));
 
228
 
 
229
    static const size_t MAX_DISPLAY_NAME_SIZE = 25;
 
230
    if (displayName.size() > MAX_DISPLAY_NAME_SIZE)
 
231
        return "";
 
232
 
 
233
    return displayName;
 
234
}
 
235
 
 
236
void stripSipUriPrefix(std::string& sipUri)
 
237
{
 
238
    // Remove sip: prefix
 
239
    static const char SIP_PREFIX[] = "sip:";
 
240
    size_t found = sipUri.find(SIP_PREFIX);
 
241
 
 
242
    if (found != std::string::npos)
 
243
        sipUri.erase(found, found + (sizeof SIP_PREFIX) - 1);
 
244
 
 
245
    found = sipUri.find("@");
 
246
 
 
247
    if (found != std::string::npos)
 
248
        sipUri.erase(found);
 
249
}
 
250
 
 
251
pj_bool_t transaction_request_cb(pjsip_rx_data *rdata)
 
252
{
 
253
    pjsip_method *method = &rdata->msg_info.msg->line.req.method;
 
254
 
 
255
    if (method->id == PJSIP_ACK_METHOD && pjsip_rdata_get_dlg(rdata))
 
256
        return true;
 
257
 
 
258
    pjsip_sip_uri *sip_to_uri = (pjsip_sip_uri *) pjsip_uri_get_uri(rdata->msg_info.to->uri);
 
259
    pjsip_sip_uri *sip_from_uri = (pjsip_sip_uri *) pjsip_uri_get_uri(rdata->msg_info.from->uri);
 
260
    std::string userName(sip_to_uri->user.ptr, sip_to_uri->user.slen);
 
261
    std::string server(sip_from_uri->host.ptr, sip_from_uri->host.slen);
 
262
    std::string account_id(Manager::instance().getAccountIdFromNameAndServer(userName, server));
 
263
 
 
264
    std::string displayName(parseDisplayName(rdata->msg_info.msg_buf));
 
265
 
 
266
    if (method->id == PJSIP_OTHER_METHOD) {
 
267
        pj_str_t *str = &method->name;
 
268
        std::string request(str->ptr, str->slen);
 
269
 
 
270
        if (request.find("NOTIFY") != (size_t)-1) {
 
271
            int voicemail;
 
272
 
 
273
            if (sscanf((const char*)rdata->msg_info.msg->body->data, "Voice-Message: %d/", &voicemail) == 1 && voicemail != 0)
 
274
                Manager::instance().startVoiceMessageNotification(account_id, voicemail);
 
275
        }
 
276
 
 
277
        pjsip_endpt_respond_stateless(endpt_, rdata, PJSIP_SC_OK, NULL, NULL, NULL);
 
278
 
 
279
        return true;
 
280
    } else if (method->id == PJSIP_OPTIONS_METHOD) {
 
281
        handleIncomingOptions(rdata);
 
282
        return true;
 
283
    } else if (method->id != PJSIP_INVITE_METHOD && method->id != PJSIP_ACK_METHOD) {
 
284
        pjsip_endpt_respond_stateless(endpt_, rdata, PJSIP_SC_METHOD_NOT_ALLOWED, NULL, NULL, NULL);
 
285
        return true;
 
286
    }
 
287
 
 
288
    SIPAccount *account = dynamic_cast<SIPAccount *>(Manager::instance().getAccount(account_id));
 
289
 
 
290
    pjmedia_sdp_session *r_sdp;
 
291
    pjsip_msg_body *body = rdata->msg_info.msg->body;
 
292
 
 
293
    if (!body || pjmedia_sdp_parse(rdata->tp_info.pool, (char*) body->data, body->len, &r_sdp) != PJ_SUCCESS)
 
294
        r_sdp = NULL;
 
295
 
 
296
    if (account->getActiveCodecs().empty()) {
 
297
        pjsip_endpt_respond_stateless(endpt_, rdata,
 
298
                                      PJSIP_SC_NOT_ACCEPTABLE_HERE, NULL, NULL,
 
299
                                      NULL);
 
300
        return false;
 
301
    }
 
302
 
 
303
    // Verify that we can handle the request
 
304
    unsigned options = 0;
 
305
 
 
306
    if (pjsip_inv_verify_request(rdata, &options, NULL, NULL, endpt_, NULL) != PJ_SUCCESS) {
 
307
        pjsip_endpt_respond_stateless(endpt_, rdata, PJSIP_SC_METHOD_NOT_ALLOWED, NULL, NULL, NULL);
 
308
        return true;
 
309
    }
 
310
 
 
311
    if (Manager::instance().hookPreference.getSipEnabled()) {
 
312
        std::string header_value(fetchHeaderValue(rdata->msg_info.msg, Manager::instance().hookPreference.getUrlSipField()));
 
313
        UrlHook::runAction(Manager::instance().hookPreference.getUrlCommand(), header_value);
 
314
    }
 
315
 
 
316
    SIPCall* call = new SIPCall(Manager::instance().getNewCallID(), Call::INCOMING, cp_);
 
317
    Manager::instance().associateCallToAccount(call->getCallId(), account_id);
 
318
 
 
319
    // May use the published address as well
 
320
    std::string addrToUse = SIPVoIPLink::instance()->getInterfaceAddrFromName(account->getLocalInterface());
 
321
    std::string addrSdp = account->isStunEnabled()
 
322
                          ? account->getPublishedAddress()
 
323
                          : addrToUse;
 
324
 
 
325
    pjsip_tpselector *tp = SIPVoIPLink::instance()->initTransportSelector(account->transport_, call->getMemoryPool());
 
326
 
 
327
    if (addrToUse == "0.0.0.0")
 
328
        addrToUse = getSIPLocalIP();
 
329
 
 
330
    if (addrSdp == "0.0.0.0")
 
331
        addrSdp = addrToUse;
 
332
 
 
333
    char tmp[PJSIP_MAX_URL_SIZE];
 
334
    int length = pjsip_uri_print(PJSIP_URI_IN_FROMTO_HDR, sip_from_uri, tmp, PJSIP_MAX_URL_SIZE);
 
335
    std::string peerNumber(tmp, length);
 
336
    stripSipUriPrefix(peerNumber);
 
337
 
 
338
    call->setConnectionState(Call::PROGRESSING);
 
339
    call->setPeerNumber(peerNumber);
 
340
    call->setDisplayName(displayName);
 
341
    call->initRecFilename(peerNumber);
 
342
 
 
343
    setCallMediaLocal(call, addrToUse);
 
344
 
 
345
    call->getLocalSDP()->setLocalIP(addrSdp);
 
346
 
 
347
    call->getAudioRtp().initAudioRtpConfig();
 
348
    call->getAudioRtp().initAudioSymmetricRtpSession();
 
349
 
 
350
    if (rdata->msg_info.msg->body) {
 
351
        char sdpbuffer[1000];
 
352
        int len = rdata->msg_info.msg->body->print_body(rdata->msg_info.msg->body, sdpbuffer, sizeof sdpbuffer);
 
353
 
 
354
        if (len == -1) // error
 
355
            len = 0;
 
356
 
 
357
        std::string sdpoffer(sdpbuffer, len);
 
358
        size_t start = sdpoffer.find("a=crypto:");
 
359
 
 
360
        // Found crypto header in SDP
 
361
        if (start != std::string::npos) {
 
362
            CryptoOffer crypto_offer;
 
363
            crypto_offer.push_back(std::string(sdpoffer.substr(start, (sdpoffer.size() - start) - 1)));
 
364
 
 
365
            std::vector<sfl::CryptoSuiteDefinition>localCapabilities;
 
366
 
 
367
            for (int i = 0; i < 3; i++)
 
368
                localCapabilities.push_back(sfl::CryptoSuites[i]);
 
369
 
 
370
            sfl::SdesNegotiator sdesnego(localCapabilities, crypto_offer);
 
371
 
 
372
            if (sdesnego.negotiate()) {
 
373
                call->getAudioRtp().setRemoteCryptoInfo(sdesnego);
 
374
                call->getAudioRtp().initLocalCryptoInfo();
 
375
            }
 
376
        }
 
377
    }
 
378
 
 
379
    call->getLocalSDP()->receiveOffer(r_sdp, account->getActiveCodecs());
 
380
 
 
381
    sfl::Codec* audiocodec = Manager::instance().audioCodecFactory.instantiateCodec(PAYLOAD_CODEC_ULAW);
 
382
    call->getAudioRtp().start(static_cast<sfl::AudioCodec *>(audiocodec));
 
383
 
 
384
    pjsip_dialog* dialog;
 
385
 
 
386
    if (pjsip_dlg_create_uas(pjsip_ua_instance(), rdata, NULL, &dialog) != PJ_SUCCESS) {
 
387
        delete call;
 
388
        pjsip_endpt_respond_stateless(endpt_, rdata, PJSIP_SC_INTERNAL_SERVER_ERROR, NULL, NULL, NULL);
 
389
        return false;
 
390
    }
 
391
 
 
392
    pjsip_inv_create_uas(dialog, rdata, call->getLocalSDP()->getLocalSdpSession(), 0, &call->inv);
 
393
 
 
394
    PJ_ASSERT_RETURN(pjsip_dlg_set_transport(dialog, tp) == PJ_SUCCESS, 1);
 
395
 
 
396
    call->inv->mod_data[mod_ua_.id] = call;
 
397
 
 
398
    // Check whether Replaces header is present in the request and process accordingly.
 
399
    pjsip_dialog *replaced_dlg;
 
400
    pjsip_tx_data *response;
 
401
 
 
402
    if (pjsip_replaces_verify_request(rdata, &replaced_dlg, PJ_FALSE, &response) != PJ_SUCCESS) {
 
403
        ERROR("Something wrong with Replaces request.");
 
404
        pjsip_endpt_respond_stateless(endpt_, rdata, 500 /* internal server error */, NULL, NULL, NULL);
 
405
    }
 
406
 
 
407
    // Check if call has been transfered
 
408
    pjsip_tx_data *tdata;
 
409
 
 
410
    if (replaced_dlg) { // If Replace header present
 
411
        // Always answer the new INVITE with 200, regardless whether
 
412
        // the replaced call is in early or confirmed state.
 
413
        if (pjsip_inv_answer(call->inv, 200, NULL, NULL, &response) == PJ_SUCCESS)
 
414
            pjsip_inv_send_msg(call->inv, response);
 
415
 
 
416
        // Get the INVITE session associated with the replaced dialog.
 
417
        pjsip_inv_session *replaced_inv = pjsip_dlg_get_inv_session(replaced_dlg);
 
418
 
 
419
        // Disconnect the "replaced" INVITE session.
 
420
        if (pjsip_inv_end_session(replaced_inv, PJSIP_SC_GONE, NULL, &tdata) == PJ_SUCCESS && tdata)
 
421
            pjsip_inv_send_msg(replaced_inv, tdata);
 
422
    } else { // Prooceed with normal call flow
 
423
        PJ_ASSERT_RETURN(pjsip_inv_initial_answer(call->inv, rdata, PJSIP_SC_RINGING, NULL, NULL, &tdata) == PJ_SUCCESS, 1);
 
424
        PJ_ASSERT_RETURN(pjsip_inv_send_msg(call->inv, tdata) == PJ_SUCCESS, 1);
 
425
 
 
426
        call->setConnectionState(Call::RINGING);
 
427
 
 
428
        Manager::instance().incomingCall(call, account_id);
 
429
        Manager::instance().getAccountLink(account_id)->addCall(call);
 
430
    }
 
431
 
 
432
    return true;
 
433
}
166
434
} // end anonymous namespace
167
435
 
168
436
/*************************************************************************************************/
170
438
SIPVoIPLink::SIPVoIPLink() : transportMap_(), evThread_(new EventThread(this))
171
439
{
172
440
#define TRY(ret) do { \
173
 
                if (ret != PJ_SUCCESS) \
174
 
                        throw VoipLinkException(#ret " failed"); \
175
 
                } while(0)
 
441
    if (ret != PJ_SUCCESS) \
 
442
    throw VoipLinkException(#ret " failed"); \
 
443
} while(0)
176
444
 
177
445
    srand(time(NULL)); // to get random number for RANDOM_PORT
178
446
 
179
447
    TRY(pj_init());
180
448
    TRY(pjlib_util_init());
181
 
    pj_log_set_level(0);    // From 0 (min) to 6 (max)
 
449
    // From 0 (min) to 6 (max)
 
450
    pj_log_set_level(Logger::getDebugMode() ? 6 : 0);
182
451
    TRY(pjnath_init());
183
452
 
184
453
    pj_caching_pool_init(cp_, &pj_pool_factory_default_policy, 0);
295
564
 
296
565
    std::string srvUri(account->getServerUri());
297
566
 
298
 
    std::string address, port;
299
 
    findLocalAddressFromUri(srvUri, account->transport_, address, port);
300
 
 
301
 
    std::string from(account->getFromUri());
302
 
    pj_str_t pjFrom = pj_str((char*) from.c_str());
303
 
    std::string contact(account->getContactHeader(address, port));
304
 
    pj_str_t pjContact = pj_str((char*) contact.c_str());
 
567
    // std::string address, port;
 
568
    // findLocalAddressFromUri(srvUri, account->transport_, address, port);
305
569
    pj_str_t pjSrv = pj_str((char*) srvUri.c_str());
306
570
 
 
571
    // Generate the FROM header
 
572
    std::string from(account->getFromUri());
 
573
    pj_str_t pjFrom = pj_str((char*) from.c_str());
 
574
 
 
575
    // Get the contact header for this account
 
576
    std::string contact(account->getContactHeader());
 
577
    pj_str_t pjContact = pj_str((char*) contact.c_str());
 
578
 
307
579
    if (pjsip_regc_init(regc, &pjSrv, &pjFrom, &pjFrom, 1, &pjContact, account->getRegistrationExpire()) != PJ_SUCCESS)
308
580
        throw VoipLinkException("Unable to initialize account registration structure");
309
581
 
345
617
    pjsip_transport_dec_ref(account->transport_);
346
618
 
347
619
    account->setRegistrationInfo(regc);
 
620
 
 
621
    // start the periodic registration request based on Expire header
 
622
    // account determines itself if a keep alive is required
 
623
    account->startKeepAliveTimer();
348
624
}
349
625
 
350
626
void SIPVoIPLink::sendUnregister(Account *a)
352
628
    SIPAccount *account = dynamic_cast<SIPAccount *>(a);
353
629
 
354
630
    // This may occurs if account failed to register and is in state INVALID
355
 
    if (!account->isRegister()) {
 
631
    if (!account->isRegistered()) {
356
632
        account->setRegistrationState(Unregistered);
357
633
        return;
358
634
    }
359
635
 
 
636
    // Make sure to cancel any ongoing timers before unregister
 
637
    account->stopKeepAliveTimer();
 
638
 
360
639
    pjsip_regc *regc = account->getRegistrationInfo();
361
640
 
362
641
    if (!regc)
373
652
    account->setRegister(false);
374
653
}
375
654
 
 
655
void SIPVoIPLink::registerKeepAliveTimer(pj_timer_entry& timer, pj_time_val& delay)
 
656
{
 
657
    pj_status_t status;
 
658
 
 
659
    status = pjsip_endpt_schedule_timer(endpt_, &timer, &delay);
 
660
    if (status != PJ_SUCCESS)
 
661
        ERROR("Could not schedule new timer in pjsip endpoint");
 
662
}
 
663
 
 
664
void SIPVoIPLink::cancelKeepAliveTimer(pj_timer_entry& timer)
 
665
{
 
666
    pjsip_endpt_cancel_timer(endpt_, &timer);
 
667
}
 
668
 
376
669
Call *SIPVoIPLink::newOutgoingCall(const std::string& id, const std::string& toUrl)
377
670
{
378
671
    SIPAccount *account = dynamic_cast<SIPAccount *>(Manager::instance().getAccount(Manager::instance().getAccountFromCall(id)));
380
673
    if (account == NULL) // TODO: We should investigate how we could get rid of this error and create a IP2IP call instead
381
674
        throw VoipLinkException("Could not get account for this call");
382
675
 
383
 
    SIPCall* call = new SIPCall(id, Call::Outgoing, cp_);
 
676
    SIPCall* call = new SIPCall(id, Call::OUTGOING, cp_);
384
677
 
385
678
    // If toUri is not a well formated sip URI, use account information to process it
386
679
    std::string toUri;
427
720
        throw VoipLinkException("Could not start rtp session for early media");
428
721
    }
429
722
 
430
 
    call->initRecFileName(toUrl);
 
723
    call->initRecFilename(toUrl);
431
724
 
432
725
    call->getLocalSDP()->setLocalIP(addrSdp);
433
726
    call->getLocalSDP()->createOffer(account->getActiveCodecs());
456
749
    if (pjsip_inv_send_msg(call->inv, tdata) != PJ_SUCCESS)
457
750
        throw VoipLinkException("Could not send invite request answer (200 OK)");
458
751
 
459
 
    call->setConnectionState(Call::Connected);
460
 
    call->setState(Call::Active);
 
752
    call->setConnectionState(Call::CONNECTED);
 
753
    call->setState(Call::ACTIVE);
461
754
}
462
755
 
463
756
void
527
820
SIPVoIPLink::onhold(const std::string& id)
528
821
{
529
822
    SIPCall *call = getSIPCall(id);
530
 
    call->setState(Call::Hold);
 
823
    call->setState(Call::HOLD);
531
824
    call->getAudioRtp().stop();
532
825
 
533
826
    Sdp *sdpSession = call->getLocalSDP();
579
872
    sdpSession->addAttributeToLocalAudioMedia("sendrecv");
580
873
 
581
874
    if (SIPSessionReinvite(call) == PJ_SUCCESS)
582
 
        call->setState(Call::Active);
 
875
        call->setState(Call::ACTIVE);
583
876
}
584
877
 
585
878
void
695
988
{
696
989
    SIPCall *call = getSIPCall(id);
697
990
 
698
 
    if (!call->isIncoming() or call->getConnectionState() == Call::Connected)
 
991
    if (!call->isIncoming() or call->getConnectionState() == Call::CONNECTED)
699
992
        return;
700
993
 
701
994
    call->getAudioRtp().stop();
726
1019
    std::string accountID(Manager::instance().getAccountFromCall(id));
727
1020
    SIPAccount *account = static_cast<SIPAccount*>(Manager::instance().getAccount(accountID));
728
1021
 
729
 
    if (account) try {
 
1022
    if (account) {
 
1023
        try {
730
1024
            dtmfSend(getSIPCall(id), code, account->getDtmfType());
731
 
        } catch (VoipLinkException) {
 
1025
        } catch (const VoipLinkException &e) {
732
1026
            // don't do anything if call doesn't exist
733
1027
        }
 
1028
    }
734
1029
}
735
1030
 
736
1031
void
737
 
SIPVoIPLink::dtmfSend(SIPCall *call, char code, DtmfType dtmf)
 
1032
SIPVoIPLink::dtmfSend(SIPCall *call, char code, const std::string &dtmf)
738
1033
{
739
 
    if (dtmf == OVERRTP) {
 
1034
    if (dtmf == SIPAccount::OVERRTP_STR) {
740
1035
        call->getAudioRtp().sendDtmfDigit(code - '0');
741
1036
        return;
742
1037
    }
743
 
 
 
1038
    else if (dtmf != SIPAccount::SIPINFO_STR) {
 
1039
        WARN("SIPVoIPLink: Unknown DTMF type %s, defaulting to %s instead",
 
1040
             dtmf.c_str(), SIPAccount::SIPINFO_STR);
 
1041
    }
744
1042
    // else : dtmf == SIPINFO
745
1043
 
746
 
    pj_str_t methodName = pj_str((char*)"INFO");
 
1044
    pj_str_t methodName = pj_str((char*) "INFO");
747
1045
    pjsip_method method;
748
1046
    pjsip_method_init_np(&method, &methodName);
749
1047
 
759
1057
 
760
1058
    /* Create "application/dtmf-relay" message body. */
761
1059
    pj_str_t content = pj_str(dtmf_body);
762
 
    pj_str_t type = pj_str((char*)"application");
763
 
    pj_str_t subtype = pj_str((char*)"dtmf-relay");
 
1060
    pj_str_t type = pj_str((char*) "application");
 
1061
    pj_str_t subtype = pj_str((char*) "dtmf-relay");
764
1062
    tdata->msg->body = pjsip_msg_body_create(tdata->pool, &type, &subtype, &content);
765
1063
 
766
1064
    if (tdata->msg->body == NULL)
780
1078
 
781
1079
    std::string toUri(call->getPeerNumber()); // expecting a fully well formed sip uri
782
1080
 
783
 
    std::string address, port;
784
 
    findLocalAddressFromUri(toUri, account->transport_, address, port);
 
1081
    // std::string address, port;
 
1082
    // findLocalAddressFromUri(toUri, account->transport_, address, port);
785
1083
 
786
 
    std::string from(account->getFromUri());
787
 
    pj_str_t pjFrom = pj_str((char*) from.c_str());
788
 
    std::string contact(account->getContactHeader(address, port));
789
 
    pj_str_t pjContact = pj_str((char*) contact.c_str());
790
1084
    pj_str_t pjTo = pj_str((char*) toUri.c_str());
791
1085
 
792
 
    pjsip_dialog *dialog;
 
1086
    // Create the from header
 
1087
    std::string from(account->getFromUri());
 
1088
    pj_str_t pjFrom = pj_str((char*) from.c_str());
 
1089
 
 
1090
    // Get the contact header
 
1091
    std::string contact(account->getContactHeader());
 
1092
    pj_str_t pjContact = pj_str((char*) contact.c_str());
 
1093
 
 
1094
    pjsip_dialog *dialog = NULL;
793
1095
 
794
1096
    if (pjsip_dlg_create_uac(pjsip_ua_instance(), &pjFrom, &pjContact, &pjTo, NULL, &dialog) != PJ_SUCCESS)
795
1097
        return false;
817
1119
    if (pjsip_inv_send_msg(call->inv, tdata) != PJ_SUCCESS)
818
1120
        return false;
819
1121
 
820
 
    call->setConnectionState(Call::Progressing);
821
 
    call->setState(Call::Active);
 
1122
    call->setConnectionState(Call::PROGRESSING);
 
1123
    call->setState(Call::ACTIVE);
822
1124
    addCall(call);
823
1125
 
824
1126
    return true;
847
1149
void
848
1150
SIPVoIPLink::SIPCallAnswered(SIPCall *call, pjsip_rx_data *rdata UNUSED)
849
1151
{
850
 
    if (call->getConnectionState() != Call::Connected) {
851
 
        call->setConnectionState(Call::Connected);
852
 
        call->setState(Call::Active);
 
1152
    if (call->getConnectionState() != Call::CONNECTED) {
 
1153
        call->setConnectionState(Call::CONNECTED);
 
1154
        call->setState(Call::ACTIVE);
853
1155
        Manager::instance().peerAnsweredCall(call->getCallId());
854
1156
    }
855
1157
}
873
1175
    if (!account)
874
1176
        return false;
875
1177
 
876
 
    SIPCall *call = new SIPCall(id, Call::Outgoing, cp_);
877
 
    call->setCallConfiguration(Call::IPtoIP);
878
 
    call->initRecFileName(to);
 
1178
    SIPCall *call = new SIPCall(id, Call::OUTGOING, cp_);
 
1179
    call->setIPToIP(true);
 
1180
    call->initRecFilename(to);
879
1181
 
880
1182
    std::string localAddress(getInterfaceAddrFromName(account->getLocalInterface()));
881
1183
 
940
1242
// Private functions
941
1243
///////////////////////////////////////////////////////////////////////////////
942
1244
 
943
 
static pj_bool_t stun_sock_on_status_cb(pj_stun_sock *stun_sock UNUSED, pj_stun_sock_op op UNUSED, pj_status_t status)
 
1245
pj_bool_t stun_sock_on_status_cb(pj_stun_sock *stun_sock UNUSED, pj_stun_sock_op op UNUSED, pj_status_t status)
944
1246
{
945
1247
    return status == PJ_SUCCESS;
946
1248
}
947
1249
 
948
 
static pj_bool_t stun_sock_on_rx_data_cb(pj_stun_sock *stun_sock UNUSED, void *pkt UNUSED, unsigned pkt_len UNUSED, const pj_sockaddr_t *src_addr UNUSED, unsigned addr_len UNUSED)
 
1250
pj_bool_t stun_sock_on_rx_data_cb(pj_stun_sock *stun_sock UNUSED, void *pkt UNUSED, unsigned pkt_len UNUSED, const pj_sockaddr_t *src_addr UNUSED, unsigned addr_len UNUSED)
949
1251
{
950
1252
    return PJ_TRUE;
951
1253
}
1107
1409
        transportMap_[account->getLocalPort()] = account->transport_;
1108
1410
}
1109
1411
 
1110
 
pjsip_tpselector *SIPVoIPLink::initTransportSelector(pjsip_transport *transport, pj_pool_t *tp_pool)
 
1412
pjsip_tpselector *SIPVoIPLink::initTransportSelector(pjsip_transport *transport, pj_pool_t *tp_pool) const
1111
1413
{
1112
1414
    assert(transport);
1113
1415
    pjsip_tpselector *tp = (pjsip_tpselector *) pj_pool_zalloc(tp_pool, sizeof(pjsip_tpselector));
1176
1478
    }
1177
1479
}
1178
1480
 
1179
 
 
1180
 
void SIPVoIPLink::findLocalAddressFromUri(const std::string& uri, pjsip_transport *transport, std::string& addr, std::string &port)
 
1481
void SIPVoIPLink::findLocalAddressFromTransport(pjsip_transport *transport, pjsip_transport_type_e transportType, std::string &addr, std::string &port) const
1181
1482
{
 
1483
    // Initialize the sip port with the default SIP port
1182
1484
    std::stringstream ss;
1183
1485
    ss << DEFAULT_SIP_PORT;
1184
1486
    port = ss.str();
1185
1487
 
1186
 
    pjsip_uri *genericUri = pjsip_parse_uri(pool_, (char*)uri.data(), uri.size(), 0);
1187
 
 
 
1488
    // Initialize the sip address with the hostname
1188
1489
    const pj_str_t *pjMachineName = pj_gethostname();
1189
1490
    addr = std::string(pjMachineName->ptr, pjMachineName->slen);
1190
1491
 
1191
 
    if (genericUri == NULL)
1192
 
        return;
1193
 
 
1194
 
    pjsip_sip_uri *sip_uri = (pjsip_sip_uri*) pjsip_uri_get_uri(genericUri);
1195
 
 
1196
 
    if (sip_uri == NULL)
1197
 
        return;
1198
 
 
1199
 
    pjsip_transport_type_e transportType;
1200
 
 
1201
 
    if (PJSIP_URI_SCHEME_IS_SIPS(sip_uri)) {
1202
 
        transportType = PJSIP_TRANSPORT_TLS;
1203
 
        ss.str("");
1204
 
        ss << DEFAULT_SIP_TLS_PORT;
1205
 
        port = ss.str();
1206
 
    } else {
1207
 
        if (transport == NULL)
1208
 
            transport = localUDPTransport_;
1209
 
 
1210
 
        transportType = PJSIP_TRANSPORT_UDP;
 
1492
    // Update address and port with active transport
 
1493
    if (!transport) {
 
1494
        ERROR("SIPVoIPLink: Transport is NULL in findLocalAddress, using local address %s:%s", addr.c_str(), port.c_str());
 
1495
        return;
1211
1496
    }
1212
1497
 
 
1498
    // get the transport manager associated with the SIP enpoint
1213
1499
    pjsip_tpmgr *tpmgr = pjsip_endpt_get_tpmgr(endpt_);
1214
 
 
1215
 
    if (!tpmgr)
1216
 
        return;
1217
 
 
1218
 
    pjsip_tpselector *tp_sel = NULL;
1219
 
 
1220
 
    if (transportType == PJSIP_TRANSPORT_UDP and transport)
1221
 
        tp_sel = initTransportSelector(transport, pool_);
 
1500
    if (!tpmgr) {
 
1501
        ERROR("SIPVoIPLink: Transport manager is NULL in findLocalAddress, using local address %s:%s", addr.c_str(), port.c_str());
 
1502
        return;
 
1503
    }
 
1504
 
 
1505
    // initialize a transport selector
 
1506
    // TODO Need to determine why we exclude TLS here...
 
1507
    // if (transportType == PJSIP_TRANSPORT_UDP and transport_)
 
1508
    pjsip_tpselector *tp_sel = initTransportSelector(transport, pool_);
 
1509
    if (!tp_sel) {
 
1510
        ERROR("SIPVoIPLink: Could not initialize transport selector, using local address %s:%s", addr.c_str(), port.c_str());
 
1511
        return;
 
1512
    }
1222
1513
 
1223
1514
    pj_str_t localAddress = {0,0};
1224
1515
    int i_port = 0;
1225
1516
 
1226
 
    if (pjsip_tpmgr_find_local_addr(tpmgr, pool_, transportType, tp_sel, &localAddress, &i_port) != PJ_SUCCESS)
 
1517
    // Find the local address and port for this transport
 
1518
    if (pjsip_tpmgr_find_local_addr(tpmgr, pool_, transportType, tp_sel, &localAddress, &i_port) != PJ_SUCCESS) {
 
1519
        WARN("SIPVoIPLink: Could not retreive local address and port from transport, using %s:%s", addr.c_str(), port.c_str());
1227
1520
        return;
 
1521
    }
1228
1522
 
 
1523
    // Update local address based on the transport type
1229
1524
    addr = std::string(localAddress.ptr, localAddress.slen);
1230
1525
 
 
1526
    // Fallback on local ip provided by pj_gethostip()
1231
1527
    if (addr == "0.0.0.0")
1232
1528
        addr = getSIPLocalIP();
1233
1529
 
 
1530
    // Determine the local port based on transport information
1234
1531
    ss.str("");
1235
1532
    ss << i_port;
1236
1533
    port = ss.str();
1237
1534
}
1238
1535
 
1239
 
 
1240
1536
namespace {
1241
 
std::string parseDisplayName(const char * buffer)
1242
 
{
1243
 
    // Parse the display name from "From" header
1244
 
    const char* from_header = strstr(buffer, "From: ");
1245
 
 
1246
 
    if (!from_header)
1247
 
        return "";
1248
 
 
1249
 
    std::string temp(from_header);
1250
 
    size_t begin_displayName = temp.find("\"") + 1;
1251
 
    size_t end_displayName = temp.rfind("\"");
1252
 
    std::string displayName(temp.substr(begin_displayName, end_displayName - begin_displayName));
1253
 
 
1254
 
    static const size_t MAX_DISPLAY_NAME_SIZE = 25;
1255
 
    if (displayName.size() > MAX_DISPLAY_NAME_SIZE)
1256
 
        return "";
1257
 
 
1258
 
    return displayName;
1259
 
}
1260
 
 
1261
 
void stripSipUriPrefix(std::string& sipUri)
1262
 
{
1263
 
    // Remove sip: prefix
1264
 
    static const char SIP_PREFIX[] = "sip:";
1265
 
    size_t found = sipUri.find(SIP_PREFIX);
1266
 
 
1267
 
    if (found != std::string::npos)
1268
 
        sipUri.erase(found, found + (sizeof SIP_PREFIX) - 1);
1269
 
 
1270
 
    found = sipUri.find("@");
1271
 
 
1272
 
    if (found != std::string::npos)
1273
 
        sipUri.erase(found);
1274
 
}
1275
 
 
1276
1537
int SIPSessionReinvite(SIPCall *call)
1277
1538
{
1278
1539
    pjsip_tx_data *tdata;
1287
1548
 
1288
1549
void invite_session_state_changed_cb(pjsip_inv_session *inv, pjsip_event *e)
1289
1550
{
1290
 
    SIPCall *call = reinterpret_cast<SIPCall*>(inv->mod_data[mod_ua_.id]);
 
1551
    SIPCall *call = static_cast<SIPCall*>(inv->mod_data[mod_ua_.id]);
1291
1552
 
1292
1553
    if (call == NULL)
1293
1554
        return;
1306
1567
    }
1307
1568
 
1308
1569
    if (inv->state == PJSIP_INV_STATE_EARLY and e->body.tsx_state.tsx->role == PJSIP_ROLE_UAC) {
1309
 
        call->setConnectionState(Call::Ringing);
 
1570
        call->setConnectionState(Call::RINGING);
1310
1571
        Manager::instance().peerRingingCall(call->getCallId());
1311
1572
    } else if (inv->state == PJSIP_INV_STATE_CONFIRMED) {
1312
1573
        // After we sent or received a ACK - The connection is established
1357
1618
    pjsip_inv_set_sdp_answer(call->inv, call->getLocalSDP()->getLocalSdpSession());
1358
1619
}
1359
1620
 
1360
 
static void sdp_create_offer_cb(pjsip_inv_session *inv, pjmedia_sdp_session **p_offer)
 
1621
void sdp_create_offer_cb(pjsip_inv_session *inv, pjmedia_sdp_session **p_offer)
1361
1622
{
1362
 
    SIPCall *call = reinterpret_cast<SIPCall*>(inv->mod_data[mod_ua_.id]);
 
1623
    SIPCall *call = static_cast<SIPCall*>(inv->mod_data[mod_ua_.id]);
1363
1624
    std::string accountid(Manager::instance().getAccountFromCall(call->getCallId()));
1364
1625
 
1365
1626
    SIPAccount *account = dynamic_cast<SIPAccount *>(Manager::instance().getAccount(accountid));
1387
1648
    const pjmedia_sdp_session *remote_sdp;
1388
1649
    const pjmedia_sdp_session *local_sdp;
1389
1650
 
1390
 
    SIPCall *call = reinterpret_cast<SIPCall *>(inv->mod_data[mod_ua_.id]);
 
1651
    SIPCall *call = static_cast<SIPCall *>(inv->mod_data[mod_ua_.id]);
1391
1652
 
1392
1653
    if (call == NULL) {
1393
1654
        DEBUG("UserAgent: Call declined by peer, SDP negotiation stopped");
1544
1805
    std::string formatedMessage = (char*) r_data->msg_info.msg->body->data;
1545
1806
 
1546
1807
    // Try to determine who is the recipient of the message
1547
 
    SIPCall *call = reinterpret_cast<SIPCall *>(inv->mod_data[mod_ua_.id]);
 
1808
    SIPCall *call = static_cast<SIPCall *>(inv->mod_data[mod_ua_.id]);
1548
1809
 
1549
1810
    if (!call)
1550
1811
        return;
1583
1844
    }
1584
1845
}
1585
1846
 
1586
 
void registration_cb(struct pjsip_regc_cbparam *param)
 
1847
void update_contact_header(pjsip_regc_cbparam *param, SIPAccount *account)
 
1848
{
 
1849
 
 
1850
    SIPVoIPLink *siplink = dynamic_cast<SIPVoIPLink *>(account->getVoIPLink());
 
1851
    if(siplink == NULL) {
 
1852
        ERROR("SIPVoIPLink: Could not find voip link from account");
 
1853
        return;
 
1854
    }
 
1855
 
 
1856
    pj_pool_t *pool = pj_pool_create(&cp_->factory, "tmp", 512, 512, NULL);
 
1857
    if(pool == NULL) {
 
1858
        ERROR("SIPVoIPLink: Could not create temporary memory pool in transport header");
 
1859
        return;
 
1860
    }
 
1861
 
 
1862
    if (param->contact_cnt == 0) {
 
1863
        WARN("SIPVoIPLink: No contact header in registration callback");
 
1864
        pj_pool_release(pool);
 
1865
        return;
 
1866
    }
 
1867
 
 
1868
    pjsip_contact_hdr *contact_hdr = param->contact[0];
 
1869
 
 
1870
    pjsip_sip_uri *uri = (pjsip_sip_uri*) contact_hdr->uri;
 
1871
    if (uri == NULL) {
 
1872
        ERROR("SIPVoIPLink: Could not find uri in contact header");
 
1873
        pj_pool_release(pool);
 
1874
        return;
 
1875
    }
 
1876
 
 
1877
    // TODO: make this based on transport type
 
1878
    // with pjsip_transport_get_default_port_for_type(tp_type);
 
1879
    if (uri->port == 0)
 
1880
        uri->port = DEFAULT_SIP_PORT;
 
1881
 
 
1882
    std::string recvContactHost(uri->host.ptr, uri->host.slen);
 
1883
    std::stringstream ss;
 
1884
    ss << uri->port;
 
1885
    std::string recvContactPort = ss.str();
 
1886
 
 
1887
    std::string currentAddress, currentPort;
 
1888
    siplink->findLocalAddressFromTransport(account->transport_, PJSIP_TRANSPORT_UDP, currentAddress, currentPort);
 
1889
 
 
1890
    bool updateContact = false;
 
1891
    std::string currentContactHeader = account->getContactHeader();
 
1892
 
 
1893
    size_t foundHost = currentContactHeader.find(recvContactHost);
 
1894
    if(foundHost == std::string::npos) {
 
1895
        updateContact = true;
 
1896
    }
 
1897
 
 
1898
    size_t foundPort = currentContactHeader.find(recvContactPort);
 
1899
    if(foundPort == std::string::npos) {
 
1900
        updateContact = true;
 
1901
    }
 
1902
 
 
1903
    if(updateContact) {
 
1904
        DEBUG("SIPVoIPLink: Update contact header: %s:%s\n", recvContactHost.c_str(), recvContactPort.c_str());
 
1905
        account->setContactHeader(recvContactHost, recvContactPort);
 
1906
        siplink->sendRegister(account);
 
1907
    }
 
1908
    pj_pool_release(pool);
 
1909
}
 
1910
 
 
1911
void registration_cb(pjsip_regc_cbparam *param)
1587
1912
{
1588
1913
    SIPAccount *account = static_cast<SIPAccount *>(param->token);
1589
1914
 
1590
 
    if (account == NULL)
1591
 
        return;
 
1915
    if (account == NULL) {
 
1916
        ERROR("SipVoipLink: account does'nt exist in registration callback");
 
1917
        return;
 
1918
    }
 
1919
 
 
1920
    if (param == NULL) {
 
1921
        ERROR("SipVoipLink: regsitration callback param is NULL");
 
1922
        return;
 
1923
    }
 
1924
 
 
1925
    if(account->isContactUpdateEnabled()) {
 
1926
        update_contact_header(param, account);
 
1927
    }
1592
1928
 
1593
1929
    const pj_str_t *description = pjsip_get_status_text(param->code);
1594
1930
 
1598
1934
        std::pair<int, std::string> details(param->code, state);
1599
1935
        // TODO: there id a race condition for this ressource when closing the application
1600
1936
        account->setRegistrationStateDetailed(details);
 
1937
 
 
1938
        account->setRegistrationExpire(param->expiration);
1601
1939
    }
1602
1940
 
1603
1941
    if (param->status != PJ_SUCCESS) {
1641
1979
        SIPVoIPLink::instance()->shutdownSipTransport(account);
1642
1980
 
1643
1981
    } else {
1644
 
        if (account->isRegister())
 
1982
        if (account->isRegistered())
1645
1983
            account->setRegistrationState(Registered);
1646
1984
        else {
1647
1985
            account->setRegistrationState(Unregistered);
1650
1988
    }
1651
1989
}
1652
1990
 
1653
 
 
1654
 
static void handleIncomingOptions(pjsip_rx_data *rdata)
1655
 
{
1656
 
    pjsip_tx_data *tdata;
1657
 
 
1658
 
    if (pjsip_endpt_create_response(endpt_, rdata, PJSIP_SC_OK, NULL, &tdata) != PJ_SUCCESS)
1659
 
        return;
1660
 
 
1661
 
#define ADD_HDR(hdr) do { \
1662
 
            const pjsip_hdr *cap_hdr = hdr; \
1663
 
            if (cap_hdr) \
1664
 
                pjsip_msg_add_hdr (tdata->msg, (pjsip_hdr*) pjsip_hdr_clone (tdata->pool, cap_hdr)); \
1665
 
        } while(0)
1666
 
#define ADD_CAP(cap) ADD_HDR(pjsip_endpt_get_capability(endpt_, cap, NULL));
1667
 
 
1668
 
    ADD_CAP(PJSIP_H_ALLOW);
1669
 
    ADD_CAP(PJSIP_H_ACCEPT);
1670
 
    ADD_CAP(PJSIP_H_SUPPORTED);
1671
 
    ADD_HDR(pjsip_evsub_get_allow_events_hdr(NULL));
1672
 
 
1673
 
    pjsip_response_addr res_addr;
1674
 
    pjsip_get_response_addr(tdata->pool, rdata, &res_addr);
1675
 
 
1676
 
    if (pjsip_endpt_send_response(endpt_, &res_addr, tdata, NULL, NULL) != PJ_SUCCESS)
1677
 
        pjsip_tx_data_dec_ref(tdata);
1678
 
}
1679
 
 
1680
 
 
1681
 
static pj_bool_t transaction_request_cb(pjsip_rx_data *rdata)
1682
 
{
1683
 
    pjsip_method *method = &rdata->msg_info.msg->line.req.method;
1684
 
 
1685
 
    if (method->id == PJSIP_ACK_METHOD && pjsip_rdata_get_dlg(rdata))
1686
 
        return true;
1687
 
 
1688
 
    pjsip_sip_uri *sip_to_uri = (pjsip_sip_uri *) pjsip_uri_get_uri(rdata->msg_info.to->uri);
1689
 
    pjsip_sip_uri *sip_from_uri = (pjsip_sip_uri *) pjsip_uri_get_uri(rdata->msg_info.from->uri);
1690
 
    std::string userName(sip_to_uri->user.ptr, sip_to_uri->user.slen);
1691
 
    std::string server(sip_from_uri->host.ptr, sip_from_uri->host.slen);
1692
 
    std::string account_id(Manager::instance().getAccountIdFromNameAndServer(userName, server));
1693
 
 
1694
 
    std::string displayName(parseDisplayName(rdata->msg_info.msg_buf));
1695
 
 
1696
 
    if (method->id == PJSIP_OTHER_METHOD) {
1697
 
        pj_str_t *str = &method->name;
1698
 
        std::string request(str->ptr, str->slen);
1699
 
 
1700
 
        if (request.find("NOTIFY") != (size_t)-1) {
1701
 
            int voicemail;
1702
 
 
1703
 
            if (sscanf((const char*)rdata->msg_info.msg->body->data, "Voice-Message: %d/", &voicemail) == 1 && voicemail != 0)
1704
 
                Manager::instance().startVoiceMessageNotification(account_id, voicemail);
1705
 
        }
1706
 
 
1707
 
        pjsip_endpt_respond_stateless(endpt_, rdata, PJSIP_SC_OK, NULL, NULL, NULL);
1708
 
 
1709
 
        return true;
1710
 
    } else if (method->id == PJSIP_OPTIONS_METHOD) {
1711
 
        handleIncomingOptions(rdata);
1712
 
        return true;
1713
 
    } else if (method->id != PJSIP_INVITE_METHOD && method->id != PJSIP_ACK_METHOD) {
1714
 
        pjsip_endpt_respond_stateless(endpt_, rdata, PJSIP_SC_METHOD_NOT_ALLOWED, NULL, NULL, NULL);
1715
 
        return true;
1716
 
    }
1717
 
 
1718
 
    SIPAccount *account = dynamic_cast<SIPAccount *>(Manager::instance().getAccount(account_id));
1719
 
 
1720
 
    pjmedia_sdp_session *r_sdp;
1721
 
    pjsip_msg_body *body = rdata->msg_info.msg->body;
1722
 
 
1723
 
    if (!body || pjmedia_sdp_parse(rdata->tp_info.pool, (char*) body->data, body->len, &r_sdp) != PJ_SUCCESS)
1724
 
        r_sdp = NULL;
1725
 
 
1726
 
    if (account->getActiveCodecs().empty()) {
1727
 
        pjsip_endpt_respond_stateless(endpt_, rdata,
1728
 
                                      PJSIP_SC_NOT_ACCEPTABLE_HERE, NULL, NULL,
1729
 
                                      NULL);
1730
 
        return false;
1731
 
    }
1732
 
 
1733
 
    // Verify that we can handle the request
1734
 
    unsigned options = 0;
1735
 
 
1736
 
    if (pjsip_inv_verify_request(rdata, &options, NULL, NULL, endpt_, NULL) != PJ_SUCCESS) {
1737
 
        pjsip_endpt_respond_stateless(endpt_, rdata, PJSIP_SC_METHOD_NOT_ALLOWED, NULL, NULL, NULL);
1738
 
        return true;
1739
 
    }
1740
 
 
1741
 
    if (Manager::instance().hookPreference.getSipEnabled()) {
1742
 
        std::string header_value(fetchHeaderValue(rdata->msg_info.msg, Manager::instance().hookPreference.getUrlSipField()));
1743
 
        UrlHook::runAction(Manager::instance().hookPreference.getUrlCommand(), header_value);
1744
 
    }
1745
 
 
1746
 
    SIPCall* call = new SIPCall(Manager::instance().getNewCallID(), Call::Incoming, cp_);
1747
 
    Manager::instance().associateCallToAccount(call->getCallId(), account_id);
1748
 
 
1749
 
    // May use the published address as well
1750
 
    std::string addrToUse = SIPVoIPLink::instance()->getInterfaceAddrFromName(account->getLocalInterface());
1751
 
    std::string addrSdp = account->isStunEnabled()
1752
 
                          ? account->getPublishedAddress()
1753
 
                          : addrToUse;
1754
 
 
1755
 
    pjsip_tpselector *tp = SIPVoIPLink::instance()->initTransportSelector(account->transport_, call->getMemoryPool());
1756
 
 
1757
 
    if (addrToUse == "0.0.0.0")
1758
 
        addrToUse = getSIPLocalIP();
1759
 
 
1760
 
    if (addrSdp == "0.0.0.0")
1761
 
        addrSdp = addrToUse;
1762
 
 
1763
 
    char tmp[PJSIP_MAX_URL_SIZE];
1764
 
    int length = pjsip_uri_print(PJSIP_URI_IN_FROMTO_HDR, sip_from_uri, tmp, PJSIP_MAX_URL_SIZE);
1765
 
    std::string peerNumber(tmp, length);
1766
 
    stripSipUriPrefix(peerNumber);
1767
 
 
1768
 
    call->setConnectionState(Call::Progressing);
1769
 
    call->setPeerNumber(peerNumber);
1770
 
    call->setDisplayName(displayName);
1771
 
    call->initRecFileName(peerNumber);
1772
 
 
1773
 
    setCallMediaLocal(call, addrToUse);
1774
 
 
1775
 
    call->getLocalSDP()->setLocalIP(addrSdp);
1776
 
 
1777
 
    call->getAudioRtp().initAudioRtpConfig();
1778
 
    call->getAudioRtp().initAudioSymmetricRtpSession();
1779
 
 
1780
 
    if (rdata->msg_info.msg->body) {
1781
 
        char sdpbuffer[1000];
1782
 
        int len = rdata->msg_info.msg->body->print_body(rdata->msg_info.msg->body, sdpbuffer, sizeof sdpbuffer);
1783
 
 
1784
 
        if (len == -1) // error
1785
 
            len = 0;
1786
 
 
1787
 
        std::string sdpoffer(sdpbuffer, len);
1788
 
        size_t start = sdpoffer.find("a=crypto:");
1789
 
 
1790
 
        // Found crypto header in SDP
1791
 
        if (start != std::string::npos) {
1792
 
            CryptoOffer crypto_offer;
1793
 
            crypto_offer.push_back(std::string(sdpoffer.substr(start, (sdpoffer.size() - start) - 1)));
1794
 
 
1795
 
            std::vector<sfl::CryptoSuiteDefinition>localCapabilities;
1796
 
 
1797
 
            for (int i = 0; i < 3; i++)
1798
 
                localCapabilities.push_back(sfl::CryptoSuites[i]);
1799
 
 
1800
 
            sfl::SdesNegotiator sdesnego(localCapabilities, crypto_offer);
1801
 
 
1802
 
            if (sdesnego.negotiate()) {
1803
 
                call->getAudioRtp().setRemoteCryptoInfo(sdesnego);
1804
 
                call->getAudioRtp().initLocalCryptoInfo();
1805
 
            }
1806
 
        }
1807
 
    }
1808
 
 
1809
 
    call->getLocalSDP()->receiveOffer(r_sdp, account->getActiveCodecs());
1810
 
 
1811
 
    sfl::Codec* audiocodec = Manager::instance().audioCodecFactory.instantiateCodec(PAYLOAD_CODEC_ULAW);
1812
 
    call->getAudioRtp().start(static_cast<sfl::AudioCodec *>(audiocodec));
1813
 
 
1814
 
    pjsip_dialog* dialog;
1815
 
 
1816
 
    if (pjsip_dlg_create_uas(pjsip_ua_instance(), rdata, NULL, &dialog) != PJ_SUCCESS) {
1817
 
        delete call;
1818
 
        pjsip_endpt_respond_stateless(endpt_, rdata, PJSIP_SC_INTERNAL_SERVER_ERROR, NULL, NULL, NULL);
1819
 
        return false;
1820
 
    }
1821
 
 
1822
 
    pjsip_inv_create_uas(dialog, rdata, call->getLocalSDP()->getLocalSdpSession(), 0, &call->inv);
1823
 
 
1824
 
    PJ_ASSERT_RETURN(pjsip_dlg_set_transport(dialog, tp) == PJ_SUCCESS, 1);
1825
 
 
1826
 
    call->inv->mod_data[mod_ua_.id] = call;
1827
 
 
1828
 
    // Check whether Replaces header is present in the request and process accordingly.
1829
 
    pjsip_dialog *replaced_dlg;
1830
 
    pjsip_tx_data *response;
1831
 
 
1832
 
    if (pjsip_replaces_verify_request(rdata, &replaced_dlg, PJ_FALSE, &response) != PJ_SUCCESS) {
1833
 
        ERROR("Something wrong with Replaces request.");
1834
 
        pjsip_endpt_respond_stateless(endpt_, rdata, 500 /* internal server error */, NULL, NULL, NULL);
1835
 
    }
1836
 
 
1837
 
    // Check if call has been transfered
1838
 
    pjsip_tx_data *tdata;
1839
 
 
1840
 
    if (replaced_dlg) { // If Replace header present
1841
 
        // Always answer the new INVITE with 200, regardless whether
1842
 
        // the replaced call is in early or confirmed state.
1843
 
        if (pjsip_inv_answer(call->inv, 200, NULL, NULL, &response) == PJ_SUCCESS)
1844
 
            pjsip_inv_send_msg(call->inv, response);
1845
 
 
1846
 
        // Get the INVITE session associated with the replaced dialog.
1847
 
        pjsip_inv_session *replaced_inv = pjsip_dlg_get_inv_session(replaced_dlg);
1848
 
 
1849
 
        // Disconnect the "replaced" INVITE session.
1850
 
        if (pjsip_inv_end_session(replaced_inv, PJSIP_SC_GONE, NULL, &tdata) == PJ_SUCCESS && tdata)
1851
 
            pjsip_inv_send_msg(replaced_inv, tdata);
1852
 
    } else { // Prooceed with normal call flow
1853
 
        PJ_ASSERT_RETURN(pjsip_inv_initial_answer(call->inv, rdata, PJSIP_SC_RINGING, NULL, NULL, &tdata) == PJ_SUCCESS, 1);
1854
 
        PJ_ASSERT_RETURN(pjsip_inv_send_msg(call->inv, tdata) == PJ_SUCCESS, 1);
1855
 
 
1856
 
        call->setConnectionState(Call::Ringing);
1857
 
 
1858
 
        Manager::instance().incomingCall(call, account_id);
1859
 
        Manager::instance().getAccountLink(account_id)->addCall(call);
1860
 
    }
1861
 
 
1862
 
    return true;
1863
 
}
1864
 
 
1865
 
static pj_bool_t transaction_response_cb(pjsip_rx_data *rdata)
1866
 
{
1867
 
    pjsip_dialog *dlg = pjsip_rdata_get_dlg(rdata);
1868
 
 
1869
 
    if (!dlg)
1870
 
        return PJ_SUCCESS;
1871
 
 
1872
 
    pjsip_transaction *tsx = pjsip_rdata_get_tsx(rdata);
1873
 
 
1874
 
    if (!tsx or tsx->method.id != PJSIP_INVITE_METHOD)
1875
 
        return PJ_SUCCESS;
1876
 
 
1877
 
    if (tsx->status_code / 100 == 2) {
1878
 
        /**
1879
 
         * Send an ACK message inside a transaction. PJSIP send automatically, non-2xx ACK response.
1880
 
         * ACK for a 2xx response must be send using this method.
1881
 
         */
1882
 
        pjsip_tx_data *tdata;
1883
 
        pjsip_dlg_create_request(dlg, &pjsip_ack_method, rdata->msg_info.cseq->cseq, &tdata);
1884
 
        pjsip_dlg_send_request(dlg, tdata, -1, NULL);
1885
 
    }
1886
 
 
1887
 
    return PJ_SUCCESS;
1888
 
}
1889
 
 
1890
1991
void onCallTransfered(pjsip_inv_session *inv, pjsip_rx_data *rdata)
1891
1992
{
1892
 
    SIPCall *currentCall = reinterpret_cast<SIPCall *>(inv->mod_data[mod_ua_.id]);
 
1993
    SIPCall *currentCall = static_cast<SIPCall *>(inv->mod_data[mod_ua_.id]);
1893
1994
 
1894
1995
    if (currentCall == NULL)
1895
1996
        return;
1919
2020
            break;
1920
2021
 
1921
2022
        case PJSIP_EVSUB_STATE_ACTIVE: {
1922
 
 
1923
 
            SIPVoIPLink *link = reinterpret_cast<SIPVoIPLink *>(pjsip_evsub_get_mod_data(sub, mod_ua_.id));
 
2023
            SIPVoIPLink *link = static_cast<SIPVoIPLink *>(pjsip_evsub_get_mod_data(sub, mod_ua_.id));
1924
2024
 
1925
2025
            if (!link or !event)
1926
2026
                return;
1935
2035
            pjsip_status_line status_line = { 500, *pjsip_get_status_text(500) };
1936
2036
 
1937
2037
            if (r_data->msg_info.msg->line.req.method.id == PJSIP_OTHER_METHOD and
1938
 
                    request.find("NOTIFY") != std::string::npos) {
 
2038
                request.find("NOTIFY") != std::string::npos) {
1939
2039
                pjsip_msg_body *body = r_data->msg_info.msg->body;
1940
2040
 
1941
2041
                if (!body)
1988
2088
    call->getLocalSDP()->setLocalPublishedAudioPort(callLocalExternAudioPort);
1989
2089
}
1990
2090
 
1991
 
std::string fetchHeaderValue(pjsip_msg *msg, std::string field)
 
2091
std::string fetchHeaderValue(pjsip_msg *msg, const std::string &field)
1992
2092
{
1993
2093
    pj_str_t name = pj_str((char*) field.c_str());
1994
2094
 
1995
 
    pjsip_generic_string_hdr *hdr = (pjsip_generic_string_hdr*) pjsip_msg_find_hdr_by_name(msg, &name, NULL);
 
2095
    pjsip_generic_string_hdr *hdr = static_cast<pjsip_generic_string_hdr*>(pjsip_msg_find_hdr_by_name(msg, &name, NULL));
1996
2096
 
1997
2097
    if (!hdr)
1998
2098
        return "";
2006
2106
 
2007
2107
    return value.substr(0, pos);
2008
2108
}
2009
 
 
2010
2109
} // end anonymous namespace
2011
2110
 
2012
2111
std::vector<std::string> SIPVoIPLink::getAllIpInterfaceByName()
2017
2116
    std::vector<std::string> ifaceList;
2018
2117
    ifaceList.push_back("default");
2019
2118
 
2020
 
    ifconf.ifc_buf = (char*)(ifreqs);
 
2119
    ifconf.ifc_buf = (char*) (ifreqs);
2021
2120
    ifconf.ifc_len = sizeof(ifreqs);
2022
2121
 
2023
2122
    int sock = socket(AF_INET,SOCK_STREAM,0);
2024
2123
 
2025
2124
    if (sock >= 0) {
2026
2125
        if (ioctl(sock, SIOCGIFCONF, &ifconf) >= 0)
2027
 
            for (unsigned i = 0; i < ifconf.ifc_len/sizeof(struct ifreq); i++)
 
2126
            for (unsigned i = 0; i < ifconf.ifc_len / sizeof(ifreq); ++i)
2028
2127
                ifaceList.push_back(std::string(ifreqs[i].ifr_name));
2029
2128
 
2030
2129
        close(sock);
2050
2149
    ioctl(fd, SIOCGIFADDR, &ifr);
2051
2150
    close(fd);
2052
2151
 
2053
 
    sockaddr_in *saddr_in = (struct sockaddr_in *) &ifr.ifr_addr;
 
2152
    sockaddr_in *saddr_in = (sockaddr_in *) &ifr.ifr_addr;
2054
2153
    return inet_ntoa(saddr_in->sin_addr);
2055
2154
}
2056
2155