Changeset 1477


Ignore:
Timestamp:
Oct 5, 2007 9:12:26 AM (11 years ago)
Author:
bennylp
Message:

Ticket #391: Added framework to send and receive arbitrary requests within call in PJSUA-LIB, with samples to send/receive DTMF with INFO in pjsua application

Location:
pjproject/trunk
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • pjproject/trunk/build.symbian/pjsua_libU.def

    r1424 r1477  
    4242        pjsua_call_reinvite                      @ 41 NONAME 
    4343        pjsua_call_send_im                       @ 42 NONAME 
    44         pjsua_call_send_typing_ind               @ 43 NONAME 
    45         pjsua_call_set_hold                      @ 44 NONAME 
    46         pjsua_call_set_user_data                 @ 45 NONAME 
    47         pjsua_call_xfer                          @ 46 NONAME 
    48         pjsua_call_xfer_replaces                 @ 47 NONAME 
    49         pjsua_codec_get_param                    @ 48 NONAME 
    50         pjsua_codec_set_param                    @ 49 NONAME 
    51         pjsua_codec_set_priority                 @ 50 NONAME 
    52         pjsua_conf_add_port                      @ 51 NONAME 
    53         pjsua_conf_adjust_rx_level               @ 52 NONAME 
    54         pjsua_conf_adjust_tx_level               @ 53 NONAME 
    55         pjsua_conf_connect                       @ 54 NONAME 
    56         pjsua_conf_disconnect                    @ 55 NONAME 
    57         pjsua_conf_get_active_ports              @ 56 NONAME 
    58         pjsua_conf_get_max_ports                 @ 57 NONAME 
    59         pjsua_conf_get_port_info                 @ 58 NONAME 
    60         pjsua_conf_get_signal_level              @ 59 NONAME 
    61         pjsua_conf_remove_port                   @ 60 NONAME 
    62         pjsua_config_default                     @ 61 NONAME 
    63         pjsua_config_dup                         @ 62 NONAME 
    64         pjsua_create                             @ 63 NONAME 
    65         pjsua_destroy                            @ 64 NONAME 
    66         pjsua_dump                               @ 65 NONAME 
    67         pjsua_enum_accs                          @ 66 NONAME 
    68         pjsua_enum_buddies                       @ 67 NONAME 
    69         pjsua_enum_calls                         @ 68 NONAME 
    70         pjsua_enum_codecs                        @ 69 NONAME 
    71         pjsua_enum_conf_ports                    @ 70 NONAME 
    72         pjsua_enum_snd_devs                      @ 71 NONAME 
    73         pjsua_enum_transports                    @ 72 NONAME 
    74         pjsua_get_buddy_count                    @ 73 NONAME 
    75         pjsua_get_ec_tail                        @ 74 NONAME 
    76         pjsua_get_pjmedia_endpt                  @ 75 NONAME 
    77         pjsua_get_pjsip_endpt                    @ 76 NONAME 
    78         pjsua_get_pool_factory                   @ 77 NONAME 
    79         pjsua_get_snd_dev                        @ 78 NONAME 
    80         pjsua_handle_events                      @ 79 NONAME 
    81         pjsua_im_send                            @ 80 NONAME 
    82         pjsua_im_typing                          @ 81 NONAME 
    83         pjsua_init                               @ 82 NONAME 
    84         pjsua_logging_config_default             @ 83 NONAME 
    85         pjsua_logging_config_dup                 @ 84 NONAME 
    86         pjsua_media_config_default               @ 85 NONAME 
    87         pjsua_media_transports_create            @ 86 NONAME 
    88         pjsua_msg_data_init                      @ 87 NONAME 
    89         pjsua_perror                             @ 88 NONAME 
    90         pjsua_player_create                      @ 89 NONAME 
    91         pjsua_player_destroy                     @ 90 NONAME 
    92         pjsua_player_get_conf_port               @ 91 NONAME 
    93         pjsua_player_get_port                    @ 92 NONAME 
    94         pjsua_player_set_pos                     @ 93 NONAME 
    95         pjsua_playlist_create                    @ 94 NONAME 
    96         pjsua_pool_create                        @ 95 NONAME 
    97         pjsua_pres_dump                          @ 96 NONAME 
    98         pjsua_reconfigure_logging                @ 97 NONAME 
    99         pjsua_recorder_create                    @ 98 NONAME 
    100         pjsua_recorder_destroy                   @ 99 NONAME 
    101         pjsua_recorder_get_conf_port             @ 100 NONAME 
    102         pjsua_recorder_get_port                  @ 101 NONAME 
    103         pjsua_set_ec                             @ 102 NONAME 
    104         pjsua_set_no_snd_dev                     @ 103 NONAME 
    105         pjsua_set_null_snd_dev                   @ 104 NONAME 
    106         pjsua_set_snd_dev                        @ 105 NONAME 
    107         pjsua_start                              @ 106 NONAME 
    108         pjsua_transport_close                    @ 107 NONAME 
    109         pjsua_transport_config_default           @ 108 NONAME 
    110         pjsua_transport_config_dup               @ 109 NONAME 
    111         pjsua_transport_create                   @ 110 NONAME 
    112         pjsua_transport_get_info                 @ 111 NONAME 
    113         pjsua_transport_register                 @ 112 NONAME 
    114         pjsua_transport_set_enable               @ 113 NONAME 
    115         pjsua_verify_sip_url                     @ 114 NONAME 
     44        pjsua_call_send_request                  @ 43 NONAME 
     45        pjsua_call_send_typing_ind               @ 44 NONAME 
     46        pjsua_call_set_hold                      @ 45 NONAME 
     47        pjsua_call_set_user_data                 @ 46 NONAME 
     48        pjsua_call_update                        @ 47 NONAME 
     49        pjsua_call_xfer                          @ 48 NONAME 
     50        pjsua_call_xfer_replaces                 @ 49 NONAME 
     51        pjsua_codec_get_param                    @ 50 NONAME 
     52        pjsua_codec_set_param                    @ 51 NONAME 
     53        pjsua_codec_set_priority                 @ 52 NONAME 
     54        pjsua_conf_add_port                      @ 53 NONAME 
     55        pjsua_conf_adjust_rx_level               @ 54 NONAME 
     56        pjsua_conf_adjust_tx_level               @ 55 NONAME 
     57        pjsua_conf_connect                       @ 56 NONAME 
     58        pjsua_conf_disconnect                    @ 57 NONAME 
     59        pjsua_conf_get_active_ports              @ 58 NONAME 
     60        pjsua_conf_get_max_ports                 @ 59 NONAME 
     61        pjsua_conf_get_port_info                 @ 60 NONAME 
     62        pjsua_conf_get_signal_level              @ 61 NONAME 
     63        pjsua_conf_remove_port                   @ 62 NONAME 
     64        pjsua_config_default                     @ 63 NONAME 
     65        pjsua_config_dup                         @ 64 NONAME 
     66        pjsua_create                             @ 65 NONAME 
     67        pjsua_destroy                            @ 66 NONAME 
     68        pjsua_dump                               @ 67 NONAME 
     69        pjsua_enum_accs                          @ 68 NONAME 
     70        pjsua_enum_buddies                       @ 69 NONAME 
     71        pjsua_enum_calls                         @ 70 NONAME 
     72        pjsua_enum_codecs                        @ 71 NONAME 
     73        pjsua_enum_conf_ports                    @ 72 NONAME 
     74        pjsua_enum_snd_devs                      @ 73 NONAME 
     75        pjsua_enum_transports                    @ 74 NONAME 
     76        pjsua_get_buddy_count                    @ 75 NONAME 
     77        pjsua_get_ec_tail                        @ 76 NONAME 
     78        pjsua_get_pjmedia_endpt                  @ 77 NONAME 
     79        pjsua_get_pjsip_endpt                    @ 78 NONAME 
     80        pjsua_get_pool_factory                   @ 79 NONAME 
     81        pjsua_get_snd_dev                        @ 80 NONAME 
     82        pjsua_handle_events                      @ 81 NONAME 
     83        pjsua_im_send                            @ 82 NONAME 
     84        pjsua_im_typing                          @ 83 NONAME 
     85        pjsua_init                               @ 84 NONAME 
     86        pjsua_logging_config_default             @ 85 NONAME 
     87        pjsua_logging_config_dup                 @ 86 NONAME 
     88        pjsua_media_config_default               @ 87 NONAME 
     89        pjsua_media_transports_create            @ 88 NONAME 
     90        pjsua_msg_data_init                      @ 89 NONAME 
     91        pjsua_perror                             @ 90 NONAME 
     92        pjsua_player_create                      @ 91 NONAME 
     93        pjsua_player_destroy                     @ 92 NONAME 
     94        pjsua_player_get_conf_port               @ 93 NONAME 
     95        pjsua_player_get_port                    @ 94 NONAME 
     96        pjsua_player_set_pos                     @ 95 NONAME 
     97        pjsua_playlist_create                    @ 96 NONAME 
     98        pjsua_pool_create                        @ 97 NONAME 
     99        pjsua_pres_dump                          @ 98 NONAME 
     100        pjsua_reconfigure_logging                @ 99 NONAME 
     101        pjsua_recorder_create                    @ 100 NONAME 
     102        pjsua_recorder_destroy                   @ 101 NONAME 
     103        pjsua_recorder_get_conf_port             @ 102 NONAME 
     104        pjsua_recorder_get_port                  @ 103 NONAME 
     105        pjsua_set_ec                             @ 104 NONAME 
     106        pjsua_set_no_snd_dev                     @ 105 NONAME 
     107        pjsua_set_null_snd_dev                   @ 106 NONAME 
     108        pjsua_set_snd_dev                        @ 107 NONAME 
     109        pjsua_start                              @ 108 NONAME 
     110        pjsua_transport_close                    @ 109 NONAME 
     111        pjsua_transport_config_default           @ 110 NONAME 
     112        pjsua_transport_config_dup               @ 111 NONAME 
     113        pjsua_transport_create                   @ 112 NONAME 
     114        pjsua_transport_get_info                 @ 113 NONAME 
     115        pjsua_transport_register                 @ 114 NONAME 
     116        pjsua_transport_set_enable               @ 115 NONAME 
     117        pjsua_verify_sip_url                     @ 116 NONAME 
  • pjproject/trunk/pjsip-apps/src/pjsua/pjsua_app.c

    r1471 r1477  
    15971597 
    15981598/* 
     1599 * Handler when a transaction within a call has changed state. 
     1600 */ 
     1601static void on_call_tsx_state(pjsua_call_id call_id, 
     1602                              pjsip_transaction *tsx, 
     1603                              pjsip_event *e) 
     1604{ 
     1605    const pjsip_method info_method =  
     1606    { 
     1607        PJSIP_OTHER_METHOD, 
     1608        { "INFO", 4 } 
     1609    }; 
     1610 
     1611    if (pjsip_method_cmp(&tsx->method, &info_method)==0) { 
     1612        /* 
     1613         * Handle INFO method. 
     1614         */ 
     1615        if (tsx->role == PJSIP_ROLE_UAC &&  
     1616            (tsx->state == PJSIP_TSX_STATE_COMPLETED || 
     1617               tsx->state == PJSIP_TSX_STATE_TERMINATED && 
     1618               e->body.tsx_state.prev_state != PJSIP_TSX_STATE_COMPLETED))  
     1619        { 
     1620            /* Status of outgoing INFO request */ 
     1621            if (tsx->status_code >= 200 && tsx->status_code < 300) { 
     1622                PJ_LOG(4,(THIS_FILE,  
     1623                          "Call %d: DTMF sent successfully with INFO", 
     1624                          call_id)); 
     1625            } else if (tsx->status_code >= 300) { 
     1626                PJ_LOG(4,(THIS_FILE,  
     1627                          "Call %d: Failed to send DTMF with INFO: %d/%.*s", 
     1628                          call_id, 
     1629                          tsx->status_code, 
     1630                          (int)tsx->status_text.slen, 
     1631                          tsx->status_text.ptr)); 
     1632            } 
     1633        } else if (tsx->role == PJSIP_ROLE_UAS && 
     1634                   tsx->state == PJSIP_TSX_STATE_TRYING) 
     1635        { 
     1636            /* Answer incoming INFO with 200/OK */ 
     1637            pjsip_rx_data *rdata; 
     1638            pjsip_tx_data *tdata; 
     1639            pj_status_t status; 
     1640 
     1641            rdata = e->body.tsx_state.src.rdata; 
     1642 
     1643            if (rdata->msg_info.msg->body) { 
     1644                status = pjsip_endpt_create_response(tsx->endpt, rdata, 
     1645                                                     200, NULL, &tdata); 
     1646                if (status == PJ_SUCCESS) 
     1647                    status = pjsip_tsx_send_msg(tsx, tdata); 
     1648 
     1649                PJ_LOG(3,(THIS_FILE, "Call %d: incoming INFO:\n%.*s",  
     1650                          call_id, 
     1651                          (int)rdata->msg_info.msg->body->len, 
     1652                          rdata->msg_info.msg->body->data)); 
     1653            } else { 
     1654                status = pjsip_endpt_create_response(tsx->endpt, rdata, 
     1655                                                     400, NULL, &tdata); 
     1656                if (status == PJ_SUCCESS) 
     1657                    status = pjsip_tsx_send_msg(tsx, tdata); 
     1658            } 
     1659        } 
     1660    } 
     1661} 
     1662 
     1663 
     1664/* 
    15991665 * Callback on media state changed event. 
    16001666 * The action may connect the call to sound device, to file, or 
     
    28632929            break; 
    28642930 
     2931        case '*': 
     2932            /* Send DTMF with INFO */ 
     2933            if (current_call == -1) { 
     2934                 
     2935                PJ_LOG(3,(THIS_FILE, "No current call")); 
     2936 
     2937            } else { 
     2938                const pj_str_t SIP_INFO = pj_str("INFO"); 
     2939                pj_str_t digits; 
     2940                int call = current_call; 
     2941                int i; 
     2942                pj_status_t status; 
     2943 
     2944                if (!simple_input("DTMF strings to send (0-9*#A-B)", buf,  
     2945                                  sizeof(buf))) 
     2946                { 
     2947                        break; 
     2948                } 
     2949 
     2950                if (call != current_call) { 
     2951                    puts("Call has been disconnected"); 
     2952                    continue; 
     2953                } 
     2954 
     2955                digits = pj_str(buf); 
     2956                for (i=0; i<digits.slen; ++i) { 
     2957                    pjsua_msg_data msg_data; 
     2958                    char body[80]; 
     2959 
     2960                    pjsua_msg_data_init(&msg_data); 
     2961                    msg_data.content_type = pj_str("application/dtmf-relay"); 
     2962                     
     2963                    pj_ansi_snprintf(body, sizeof(body), 
     2964                                     "Signal=%c\r\n" 
     2965                                     "Duration=160", 
     2966                                     buf[i]); 
     2967                    msg_data.msg_body = pj_str(body); 
     2968 
     2969                    status = pjsua_call_send_request(current_call, &SIP_INFO,  
     2970                                                     &msg_data); 
     2971                    if (status != PJ_SUCCESS) { 
     2972                        break; 
     2973                    } 
     2974                } 
     2975            } 
     2976            break; 
     2977 
    28652978        case 'S': 
    28662979            /* 
     
    31513264    app_config.cfg.cb.on_call_media_state = &on_call_media_state; 
    31523265    app_config.cfg.cb.on_incoming_call = &on_incoming_call; 
     3266    app_config.cfg.cb.on_call_tsx_state = &on_call_tsx_state; 
    31533267    app_config.cfg.cb.on_dtmf_digit = &call_on_dtmf_callback; 
    31543268    app_config.cfg.cb.on_reg_state = &on_reg_state; 
  • pjproject/trunk/pjsip/include/pjsip-ua/sip_inv.h

    r1469 r1477  
    134134     * This callback is called whenever any transactions within the session 
    135135     * has changed their state. Application MAY implement this callback,  
    136      * e.g. to monitor the progress of an outgoing request. 
     136     * e.g. to monitor the progress of an outgoing request, or to send 
     137     * response to unhandled incoming request (such as INFO). 
    137138     * 
    138139     * This callback is optional. 
  • pjproject/trunk/pjsip/include/pjsua-lib/pjsua.h

    r1471 r1477  
    546546 
    547547    /** 
     548     * This is a general notification callback which is called whenever 
     549     * a transaction within the call has changed state. Application can 
     550     * implement this callback for example to monitor the state of  
     551     * outgoing requests, or to answer unhandled incoming requests  
     552     * (such as INFO) with a final response. 
     553     * 
     554     * @param call_id   Call identification. 
     555     * @param tsx       The transaction which has changed state. 
     556     * @param e         Transaction event that caused the state change. 
     557     */ 
     558    void (*on_call_tsx_state)(pjsua_call_id call_id,  
     559                              pjsip_transaction *tsx, 
     560                              pjsip_event *e); 
     561 
     562    /** 
    548563     * Notify application when media state in the call has changed. 
    549564     * Normal application would need to implement this callback, e.g. 
     
    29062921                                                pj_bool_t is_typing, 
    29072922                                                const pjsua_msg_data*msg_data); 
     2923 
     2924/** 
     2925 * Send arbitrary request with the call. This is useful for example to send 
     2926 * INFO request. Note that application should not use this function to send 
     2927 * requests which would change the invite session's state, such as re-INVITE, 
     2928 * UPDATE, PRACK, and BYE. 
     2929 * 
     2930 * @param call_id       Call identification. 
     2931 * @param method        SIP method of the request. 
     2932 * @param msg_data      Optional message body and/or list of headers to be  
     2933 *                      included in outgoing request. 
     2934 * 
     2935 * @return              PJ_SUCCESS on success, or the appropriate error code. 
     2936 */ 
     2937PJ_DECL(pj_status_t) pjsua_call_send_request(pjsua_call_id call_id, 
     2938                                             const pj_str_t *method, 
     2939                                             const pjsua_msg_data *msg_data); 
     2940 
    29082941 
    29092942/** 
  • pjproject/trunk/pjsip/src/pjsua-lib/pjsua_call.c

    r1471 r1477  
    16531653    if (status != PJ_SUCCESS) { 
    16541654        pjsua_perror(THIS_FILE, "Unable to send MESSAGE request", status); 
     1655        goto on_return; 
     1656    } 
     1657 
     1658on_return: 
     1659    pjsip_dlg_dec_lock(dlg); 
     1660    return status; 
     1661} 
     1662 
     1663 
     1664/* 
     1665 * Send arbitrary request. 
     1666 */ 
     1667PJ_DEF(pj_status_t) pjsua_call_send_request(pjsua_call_id call_id, 
     1668                                            const pj_str_t *method_str, 
     1669                                            const pjsua_msg_data *msg_data) 
     1670{ 
     1671    pjsua_call *call; 
     1672    pjsip_dialog *dlg; 
     1673    pjsip_method method; 
     1674    pjsip_tx_data *tdata; 
     1675    pj_status_t status; 
     1676 
     1677    PJ_ASSERT_RETURN(call_id>=0 && call_id<(int)pjsua_var.ua_cfg.max_calls, 
     1678                     PJ_EINVAL); 
     1679 
     1680    status = acquire_call("pjsua_call_send_request", call_id, &call, &dlg); 
     1681    if (status != PJ_SUCCESS) 
     1682        return status; 
     1683 
     1684    /* Init method */ 
     1685    pjsip_method_init_np(&method, (pj_str_t*)method_str); 
     1686 
     1687    /* Create request message. */ 
     1688    status = pjsip_dlg_create_request( call->inv->dlg, &method, -1, &tdata); 
     1689    if (status != PJ_SUCCESS) { 
     1690        pjsua_perror(THIS_FILE, "Unable to create request", status); 
     1691        goto on_return; 
     1692    } 
     1693 
     1694    /* Add additional headers etc */ 
     1695    pjsua_process_msg_data( tdata, msg_data); 
     1696 
     1697    /* Send the request. */ 
     1698    status = pjsip_dlg_send_request( call->inv->dlg, tdata, -1, NULL); 
     1699    if (status != PJ_SUCCESS) { 
     1700        pjsua_perror(THIS_FILE, "Unable to send request", status); 
    16551701        goto on_return; 
    16561702    } 
     
    28462892    PJSUA_LOCK(); 
    28472893 
     2894    /* Notify application callback first */ 
     2895    if (pjsua_var.ua_cfg.cb.on_call_tsx_state) { 
     2896        (*pjsua_var.ua_cfg.cb.on_call_tsx_state)(call->index, tsx, e); 
     2897    } 
     2898 
    28482899    if (tsx->role==PJSIP_ROLE_UAS && 
    28492900        tsx->state==PJSIP_TSX_STATE_TRYING && 
Note: See TracChangeset for help on using the changeset viewer.