Subversion Repositories tpanel

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
123 andreas 1
/*
2
 * Copyright (C) 2022 by Andreas Theofilu <andreas@theosys.at>
3
 *
4
 * This program is free software; you can redistribute it and/or modify
5
 * it under the terms of the GNU General Public License as published by
6
 * the Free Software Foundation; either version 3 of the License, or
7
 * (at your option) any later version.
8
 *
9
 * This program is distributed in the hope that it will be useful,
10
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
 * GNU General Public License for more details.
13
 *
14
 * You should have received a copy of the GNU General Public License
15
 * along with this program; if not, write to the Free Software Foundation,
16
 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301  USA
17
 */
18
 
19
#ifndef __TSIPCLIENT_H__
20
#define __TSIPCLIENT_H__
21
 
22
#include <thread>
23
#include <atomic>
24
 
135 andreas 25
#include <pjsua-lib/pjsua.h>
129 andreas 26
 
27
#ifndef _NOSIP_
135 andreas 28
#define SIP_MAX_LINES       2
124 andreas 29
 
135 andreas 30
#define current_acc         pjsua_acc_get_default()
31
 
32
#define PJSUA_APP_NO_LIMIT_DURATION (int)0x7FFFFFFF
33
// Ringtones                US         UK
34
#define RINGBACK_FREQ1      440     // 400
35
#define RINGBACK_FREQ2      480     // 450
36
#define RINGBACK_ON         2000    // 400
37
#define RINGBACK_OFF        4000    // 200
38
#define RINGBACK_CNT        1       // 2
39
#define RINGBACK_INTERVAL   4000    // 2000
40
 
41
#define RING_FREQ1          800
42
#define RING_FREQ2          640
43
#define RING_ON             200
44
#define RING_OFF            100
45
#define RING_CNT            3
46
#define RING_INTERVAL       3000
47
 
48
typedef unsigned int        uint_t;
49
 
123 andreas 50
class TSIPClient
51
{
52
    public:
124 andreas 53
        typedef enum SIP_STATE_t
54
        {
127 andreas 55
            SIP_NONE,               // Undefined state (only valid on startup before initialisation)
56
            SIP_IDLE,               // Initialized but no event
57
            SIP_CONNECTED,          // Call is in progress
58
            SIP_DISCONNECTED,       // Call has ended
59
            SIP_TRYING,             // Trying to call someone
60
            SIP_RINGING,            // Phone is ringing (incoming call)
61
            SIP_HOLD,               // Active call is paused
62
            SIP_REJECTED,           // Outgoing call was rejected
63
            SIP_ERROR               // An error occured
124 andreas 64
        }SIP_STATE_t;
65
 
127 andreas 66
        TSIPClient();
123 andreas 67
        ~TSIPClient();
68
 
135 andreas 69
        bool init();
70
 
123 andreas 71
        void cleanUp();
124 andreas 72
        int getLineID() { return mLine; }
138 andreas 73
        SIP_STATE_t getSIPState(pjsua_call_id id) { if (id >= 0 && id < PJSUA_MAX_CALLS) return mSIPState[id]; else return SIP_NONE; }
135 andreas 74
        bool isRegistered() { return mRegistered; }
141 andreas 75
        static TSIPClient *getSIPClient() { return mMyself; }
123 andreas 76
 
127 andreas 77
        bool call(const std::string& dest);         //<! Start a phone call
135 andreas 78
        bool pickup(pjsua_call_id call);            //<! Lift up if the phone is ringing
127 andreas 79
        bool terminate(int id);                     //<! Terminate a call
80
        bool hold(int id);                          //<! Pause a call
81
        bool resume(int id);                        //<! Resume a paused call
82
        bool sendDTMF(std::string& dtmf);           //<! Send a DTMF string
128 andreas 83
        bool sendLinestate();                       //<! Queries the state of each of the connections used by the SIP device.
84
        bool sendPrivate(bool state);               //<! Enables or disables the privacy feature on the phone (do not disturb).
85
        bool redial();                              //<! Redial last number
86
        bool transfer(int id, const std::string& num);  //<! transfer the current call
138 andreas 87
        bool setDTMFduration(uint_t ms);            //<! Set the DTMF duration in ms.
88
        bool getPrivate() { return mDoNotDisturb; } //<! Returns the current private mode.
123 andreas 89
 
90
    protected:
141 andreas 91
        void runRinger();                           //<! Plays a ring tone if a call is coming.
123 andreas 92
 
135 andreas 93
        static void _log_call(int level, const char *data, int len);
94
        static void on_incoming_call(pjsua_acc_id acc_id, pjsua_call_id call_id, pjsip_rx_data *rdata);
95
        static void on_call_state(pjsua_call_id call_id, pjsip_event *e);
96
        static void on_call_media_state(pjsua_call_id call_id);
97
        static void call_on_dtmf_callback2(pjsua_call_id call_id, const pjsua_dtmf_info *info);
98
        static pjsip_redirect_op call_on_redirected(pjsua_call_id call_id, const pjsip_uri *target, const pjsip_event *e);
99
        static void on_call_transfer_status(pjsua_call_id call_id, int status_code, const pj_str_t *status_text, pj_bool_t final, pj_bool_t *p_cont);
100
        static void on_transport_state(pjsip_transport *tp, pjsip_transport_state state, const pjsip_transport_state_info *info);
101
        static void on_ip_change_progress(pjsua_ip_change_op op, pj_status_t status, const pjsua_ip_change_op_info *info);
102
        static void simple_registrar(pjsip_rx_data *rdata);
103
        static pj_bool_t default_mod_on_rx_request(pjsip_rx_data *rdata);
104
        static void ringback_start(pjsua_call_id call_id);
105
        static void ring_start(pjsua_call_id call_id);
106
        static void ring_stop(pjsua_call_id call_id);
107
        static pj_bool_t find_next_call(void);
108
        static void call_timeout_callback(pj_timer_heap_t *timer_heap, struct pj_timer_entry *entry);
109
        static void on_playfile_done(pjmedia_port *port, void *usr_data);
110
        static void hangup_timeout_callback(pj_timer_heap_t *timer_heap, struct pj_timer_entry *entry);
111
 
123 andreas 112
    private:
135 andreas 113
        static pjsip_module mod_default_handler;
114
 
127 andreas 115
        int getNumberCalls();
138 andreas 116
        pjsua_call_id getActiveCall();
117
        void setSIPState(SIP_STATE_t s, pjsua_call_id id) { if (id >= 0 && id < PJSUA_MAX_CALLS) mSIPState[id] = s; }
127 andreas 118
 
135 andreas 119
        static void sendConnectionStatus(SIP_STATE_t state, int id);
141 andreas 120
        static void init_ringtone_player();
121
        static pj_status_t start_ring_tone();
122
        static pj_status_t stop_ring_tone();
138 andreas 123
 
124 andreas 124
        int mLine{0};
135 andreas 125
        bool mRegistered{false};
138 andreas 126
        SIP_STATE_t mSIPState[PJSUA_MAX_CALLS];
135 andreas 127
        pjsua_acc_id mAccountID{0};
128
        std::string mLastCall;
138 andreas 129
        uint_t mDTMFduration{PJSUA_CALL_SEND_DTMF_DURATION_DEFAULT};
130
        bool mDoNotDisturb{false};
123 andreas 131
 
135 andreas 132
        static TSIPClient *mMyself;
133
        static pjsua_call_id mCurrentCall;
134
        static std::atomic<bool> mRefreshRun;
141 andreas 135
        static bool mPhoneRingInit;
135 andreas 136
        // Here is the configuration for the PJSUA library
137
        typedef struct app_call_data
138
        {
139
            pj_timer_entry      timer;
140
            pj_bool_t           ringback_on{PJ_FALSE};
141
            pj_bool_t           ring_on{PJ_FALSE};
142
        } app_call_data;
123 andreas 143
 
141 andreas 144
        typedef struct ringtone_port_info_t
145
        {
146
            pj_bool_t ring_on{PJ_FALSE};
147
            int ring_slot{0};
148
            pjmedia_port *ring_port{nullptr};
149
            pj_pool_t *pool{nullptr};
150
        } ringtone_port_info_t;
151
 
135 andreas 152
        typedef struct pjsua_app_config
153
        {
154
            pjsua_config        cfg;
155
            pjsua_logging_config log_cfg;
156
            pjsua_media_config  media_cfg;
157
            pj_bool_t           no_refersub{PJ_FALSE};
158
            pj_bool_t           enable_qos{PJ_FALSE};
159
            pj_bool_t           no_tcp{PJ_TRUE};
160
            pj_bool_t           no_udp{PJ_FALSE};
161
            pj_bool_t           use_tls{PJ_FALSE};
162
            pjsua_transport_config  udp_cfg;
163
            pjsua_transport_config  rtp_cfg;
164
            pjsip_redirect_op   redir_op;
165
            int                 srtp_keying{0};
166
 
167
            uint_t              acc_cnt{0};
168
            pjsua_acc_config    acc_cfg[PJSUA_MAX_ACC];
169
 
170
            uint_t              buddy_cnt{0};
171
            pjsua_buddy_config  buddy_cfg[PJSUA_MAX_BUDDIES];
172
 
173
            app_call_data       call_data[PJSUA_MAX_CALLS];
174
 
175
            pj_pool_t          *pool{nullptr};
176
            /* Compatibility with older pjsua */
177
 
178
            uint_t              codec_cnt{0};
179
            pj_str_t            codec_arg[32];
180
            uint_t              codec_dis_cnt{0};
181
            pj_str_t            codec_dis[32];
182
            pj_bool_t           null_audio{PJ_FALSE};
141 andreas 183
            uint_t              wav_count{0};
135 andreas 184
            pj_str_t            wav_files[32];
185
            uint_t              tone_count{0};
186
            pjmedia_tone_desc   tones[32];
187
            pjsua_conf_port_id  tone_slots[32];
188
            pjsua_player_id     wav_id{0};
189
            pjsua_conf_port_id  wav_port{0};
190
            pj_bool_t           auto_play{PJ_FALSE};
191
            pj_bool_t           auto_play_hangup{PJ_FALSE};
192
            pj_timer_entry      auto_hangup_timer;
193
            pj_bool_t           auto_loop{PJ_FALSE};
194
            pj_bool_t           auto_conf{PJ_FALSE};
195
            pj_str_t            rec_file;
196
            pj_bool_t           auto_rec{PJ_FALSE};
197
            pjsua_recorder_id   rec_id{0};
198
            pjsua_conf_port_id  rec_port{0};
199
            unsigned            auto_answer{0};
141 andreas 200
            unsigned            duration{36000};
201
            float               mic_level{100.0};
202
            float               speaker_level{100.0};
135 andreas 203
 
204
            int                 capture_dev{0};
205
            int                 playback_dev{0};
206
            uint_t              capture_lat{0};
207
            uint_t              playback_lat{0};
208
 
209
            pj_bool_t           no_tones{PJ_FALSE};
210
            int                 ringback_slot{0};
211
            int                 ringback_cnt{0};
212
            pjmedia_port        *ringback_port{nullptr};
213
            int                 ring_slot{0};
214
            int                 ring_cnt{0};
215
            pjmedia_port        *ring_port{nullptr};
216
 
217
            uint_t              aud_cnt{0};
218
        }pjsua_app_config;
219
 
220
        static pjsua_app_config mAppConfig;
141 andreas 221
        static ringtone_port_info_t mRingtonePortInfo;
124 andreas 222
};
129 andreas 223
#endif  // _NOSIP_
224
#endif  // __TSIPCLIENT_H__