[asterisk-dev] Transfer cmd (PJSIP not sending Referred-By but chan_sip does)

Mark Michelson mmichelson at digium.com
Tue Aug 25 16:53:29 CDT 2015


Yep, that looks like what I would expect it to look like. The only thing 
that immediately jumps out as unnecessary is the

     if (ref_by_val && !ast_strlen_zero(ref_by_val))

line. You can get rid of the initial NULL check because 
ast_strlen_zero() does that for you.

If you wanted to submit this for inclusion in Asterisk, feel free to 
upload a review to https://gerrit.asterisk.org. Instructions can be 
found on the wiki [1]. Before submitting, I'd also be sure to read the 
Asterisk coding guidelines [2] since the current code would have coding 
guidelines findings on it.

[1] https://wiki.asterisk.org/wiki/display/AST/Gerrit+Usage
[2] https://wiki.asterisk.org/wiki/display/AST/Coding+Guidelines

On 08/25/2015 04:35 PM, Dan Cropp wrote:
>
> Thank you Mark for the tips.
>
> Is the code below close to what you were thinking?
>
> I ran some initial tests and it seems to be working.  I can override 
> the default Referred-By value by setting the SIPREFERREDBYHDR variable.
>
> static void transfer_refer(struct ast_sip_session *session, const char 
> *target)
>
> {
>
> pjsip_evsub *sub;
>
>         enum ast_control_transfer message = AST_TRANSFER_SUCCESS;
>
> pj_str_t tmp;
>
> pjsip_tx_data *packet;
>
>         if (pjsip_xfer_create_uac(session->inv_session->dlg, NULL, 
> &sub) != PJ_SUCCESS) {
>
>              message = AST_TRANSFER_FAILED;
>
> ast_queue_control_data(session->channel, AST_CONTROL_TRANSFER, 
> &message, sizeof(message));
>
> return;
>
>         }
>
>         if (pjsip_xfer_initiate(sub, pj_cstr(&tmp, target), &packet) 
> != PJ_SUCCESS) {
>
> message = AST_TRANSFER_FAILED;
>
> ast_queue_control_data(session->channel, AST_CONTROL_TRANSFER, 
> &message, sizeof(message));
>
> pjsip_evsub_terminate(sub, PJ_FALSE);
>
> return;
>
>         }
>
>         /**** Start of changes ****/
>
> pjsip_hdr *hdr;
>
>         const pj_str_t str_ref_by = { "Referred-By", 11 };
>
>         const char *ref_by_val = 
> pbx_builtin_getvar_helper(session->channel, "SIPREFERREDBYHDR");
>
> pj_str_t tmp2;
>
>         if (ref_by_val && !ast_strlen_zero(ref_by_val))
>
>           {
>
>             hdr = 
> (pjsip_hdr*)pjsip_generic_string_hdr_create(packet->pool, &str_ref_by, 
> pj_cstr(&tmp2, ref_by_val));
>
>           }
>
>         else
>
>           {
>
>             /* Add Referred-By header */
>
>             hdr = 
> (pjsip_hdr*)pjsip_generic_string_hdr_create(packet->pool, &str_ref_by, 
> &session->inv_session->dlg->local.info_str);
>
>           }
>
> pjsip_msg_add_hdr(packet->msg, hdr);
>
>         /**** End of changes ****/
>
> pjsip_xfer_send_request(sub, packet);
>
>       ast_queue_control_data(session->channel, AST_CONTROL_TRANSFER, 
> &message, sizeof(message));
>
> }
>
> *From:*asterisk-dev-bounces at lists.digium.com 
> [mailto:asterisk-dev-bounces at lists.digium.com] *On Behalf Of *Mark 
> Michelson
> *Sent:* Tuesday, August 25, 2015 1:17 PM
> *To:* Asterisk Developers Mailing List
> *Subject:* Re: [asterisk-dev] Transfer cmd (PJSIP not sending 
> Referred-By but chan_sip does)
>
> That code gets you about 95% of the way there.
>
> The biggest difference would be that the pjsip_msg_add_hdr() call may 
> need to be broken up based on whether the SIPREFERREDBYHDR channel 
> variable is set or not. To determine that, you can use the 
> pbx_builtin_getvar_helper() function call declared in 
> include/asterisk/pbx.h to retrieve the variable value, and the 
> ast_strlen_zero() function to determine if the channel variable value 
> is zero-length or not.
>
> Other than that, you should be able to omit the call to 
> pjsua_process_msg_data() since Asterisk doesn't use pjsua.
>
> On 08/25/2015 12:35 PM, Dan Cropp wrote:
>
>     In doing a little research, it seems the Referred-By header could
>     be added after the pjsip_xfer_initiate.
>
>     This is the approach PJSIP did for some code as far back as PJSIP 1.6.
>
>         /*
>
>          * Create REFER request.
>
>          */
>
>         status = pjsip_xfer_initiate(sub, dest, &tdata);
>
>         if (status != PJ_SUCCESS) {
>
>     pjsua_perror(THIS_FILE, "Unable to create REFER request", status);
>
>     pjsip_dlg_dec_lock(dlg);
>
>                     return status;
>
>         }
>
>         /* Add Referred-By header */
>
>         gs_hdr = pjsip_generic_string_hdr_create(tdata->pool, &str_ref_by,
>
>          &dlg->local.info_str);
>
>         pjsip_msg_add_hdr(tdata->msg, (pjsip_hdr*)gs_hdr);
>
>         /* Add additional headers etc */
>
>         pjsua_process_msg_data( tdata, msg_data);
>
>         /* Send. */
>
>         status = pjsip_xfer_send_request(sub, tdata);
>
>         if (status != PJ_SUCCESS) {
>
>     pjsua_perror(THIS_FILE, "Unable to send REFER request", status);
>
>     pjsip_dlg_dec_lock(dlg);
>
>                     return status;
>
>         }
>
>     Could anyone provider some insight into how difficult this might
>     be for me to add and submit for approval?  Depending on the
>     answer, my manager may be willing to let me work on this.
>
>     I've developed in C/C++ for over 25 years so I'm plenty familiar
>     with the language.
>
>     I'm less familiar with the syntax and coding standards of
>     Asterisk.  I know the group is very good at letting people know
>     about their mistakes and how to fix them.
>
>     Have a great day!
>
>     Dan
>
>     *From:*asterisk-dev-bounces at lists.digium.com
>     <mailto:asterisk-dev-bounces at lists.digium.com>
>     [mailto:asterisk-dev-bounces at lists.digium.com] *On Behalf Of *Dan
>     Cropp
>     *Sent:* Tuesday, August 25, 2015 10:50 AM
>     *To:* Asterisk Developers Mailing List
>     *Subject:* Re: [asterisk-dev] Transfer cmd (PJSIP not sending
>     Referred-By but chan_sip does)
>
>     Thank you Mark
>
>     *From:*asterisk-dev-bounces at lists.digium.com
>     <mailto:asterisk-dev-bounces at lists.digium.com>
>     [mailto:asterisk-dev-bounces at lists.digium.com] *On Behalf Of *Mark
>     Michelson
>     *Sent:* Tuesday, August 25, 2015 10:30 AM
>     *To:* Asterisk Developers Mailing List
>     *Subject:* Re: [asterisk-dev] Transfer cmd (PJSIP not sending
>     Referred-By but chan_sip does)
>
>     The answer to this is actually pretty simple: adding Referred-By
>     in outgoing SIP REFERs is simply not implemented in chan_pjsip's
>     chan_pjsip_transfer() function.
>
>     As far as the syntax required for the Transfer() application,
>     that's probably a case where that needs to be clarified in
>     documentation. There are lots of places in PJSIP configuration
>     where we require full SIP URIs rather than just IP addresses or
>     bare URIs (user at domain).
>
>     On 08/25/2015 10:00 AM, Dan Cropp wrote:
>
>         I asked the question on asterisk–users but did not receive a
>         response, so I am sending the question here.
>
>         I am running Asterisk 13.5.0.
>
>         A call comes in, Asterisk answers it. After some actions, the
>         call needs to be Transferred (SIP REFER) to another number. 
>         The other switch is responsible for accepting the Transfer and
>         tromboning the lines internally.  It will also send a BYE so
>         Asterisk no longer has the call.
>
>         The behavior works when I have the endpoint configured at
>         chan_sip.  It does not work when the endpoint is configured as
>         PJSIP.  I worked with the other switch vendor and he
>         determined chan_sip includes the Referred-By header.  PJSIP
>         does not include the Referred-By header.  The other switch
>         requires the Referred-By header to be present.
>
>         I tried setting the channel’s SIPREFERREDBYHDR variable before
>         the Transfer command and that still did not force the
>         Referred-By header to be part of the REFER packet.
>
>         I tried the PJSIP_HEADER add and it still did not add the
>         Referred-By header to the REFER packet.
>
>         Is there a PJSIP setting to force the Referred-By to be part
>         of the REFER packet?
>
>         chan_sip (succeeds)
>
>         19:27:32.512123 IP (tos 0x0, ttl 64, id 11492, offset 0, flags
>         [none], proto UDP (17), length 630)
>
>             192.168.xxx.xxx.sip > 192.168.yyy.yyy.sip: SIP, length: 602
>
>                 REFER sip:3400 at 192.168.yyy.yyy:5060 SIP/2.0
>
>                 Via: SIP/2.0/UDP
>         192.168.xxx.xxx:5060;branch=z9hG4bK58f4bd1d
>
>                 Max-Forwards: 70
>
>                 From: <sip:3344 at 192.168.xxx.xxx>;tag=as44000cf4
>
>                 To: <sip:3400 at 192.168.yyy.yyy>;tag=7Iy0JkwDC
>
>                 Contact: <sip:3344 at 192.168.xxx.xxx:5060>
>
>                 Call-ID: jdEuqpAK-0002- at 192.168.yyy.yyy
>         <mailto:jdEuqpAK-0002- at 192.168.yyy.yyy>
>
>                 CSeq: 102 REFER
>
>                 User-Agent: Asterisk PBX 13.5.0
>
>                 Date: Thu, 20 Aug 2015 19:27:32 GMT
>
>                 Refer-To: <sip:370 at 192.168.yyy.yyy>
>
>                 Referred-By: <sip:3344 at 192.168.xxx.xxx:5060>
>
>                 Allow: INVITE, ACK, CANCEL, OPTIONS, BYE, REFER,
>         SUBSCRIBE, NOTIFY, INFO, PUBLISH, MESSAGE
>
>                 Supported: replaces, timer
>
>                 Content-Length: 0
>
>         Pjsip
>
>         18:46:58.386372 IP (tos 0x0, ttl 64, id 38690, offset 0, flags
>         [DF], proto UDP (17), length 654)
>
>             192.168.xxx.xxx.sip > 192.168.yyy.yyy.sip: SIP, length: 626
>
>                 REFER sip:3400 at 192.168.yyy.yyy:5060 SIP/2.0
>
>                 Via: SIP/2.0/UDP
>         192.168.xxx.xxx:5060;rport;branch=z9hG4bKPjec41c3b9-d734-482d-82c1-2a6f8d9452a3
>
>                 From:
>         <sip:3344 at 192.168.xxx.xxx>;tag=3c10f423-e468-42ea-87a1-658ae106581c
>
>                 To: <sip:3400 at 192.168.yyy.yyy>;tag=WITKDakt
>
>                 Contact: <sip:192.168.xxx.xxx:5060>
>
>                 Call-ID: s6Wk6l6Q-0001- at 192.168.yyy.yyy
>         <mailto:s6Wk6l6Q-0001- at 192.168.yyy.yyy>
>
>                 CSeq: 981 REFER
>
>                 Event: refer
>
>                 Expires: 600
>
>                 Supported: 100rel, timer, replaces, norefersub
>
>                 Accept: message/sipfrag;version=2.0
>
>                 Allow-Events: message-summary, presence, dialog, refer
>
>                 Refer-To: <sip:370 at 192.168.yyy.yyy>
>
>                 Max-Forwards: 70
>
>                 User-Agent: Asterisk PBX 13.5.0
>
>                 Content-Length:  0
>
>         One other slight oddity.
>
>         To get chan_sip to Transfer
>
>         370 at 192.168.yyy.yyy <mailto:370 at 192.168.yyy.yyy>
>
>         To get PJSIP to Transfer with the correct Refer-To header, I
>         had to include the <> and sip:
>
>         <_sip:370 at 192.168.yyy.__yyy_>
>
>         Have a great day!
>
>         Dan
>
>
>
>
>

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.digium.com/pipermail/asterisk-dev/attachments/20150825/52c5c0b7/attachment-0001.html>


More information about the asterisk-dev mailing list