00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039 #include "asterisk.h"
00040
00041 ASTERISK_FILE_VERSION(__FILE__, "$Revision: 372845 $")
00042
00043 #include <sys/mman.h>
00044 #include <dirent.h>
00045 #include <sys/socket.h>
00046 #include <netinet/in.h>
00047 #include <arpa/inet.h>
00048 #include <netinet/in_systm.h>
00049 #include <netinet/ip.h>
00050 #include <sys/time.h>
00051 #include <sys/signal.h>
00052 #include <signal.h>
00053 #include <strings.h>
00054 #include <netdb.h>
00055 #include <fcntl.h>
00056 #include <sys/stat.h>
00057 #include <regex.h>
00058
00059 #include "asterisk/paths.h"
00060
00061 #include "asterisk/lock.h"
00062 #include "asterisk/frame.h"
00063 #include "asterisk/channel.h"
00064 #include "asterisk/module.h"
00065 #include "asterisk/pbx.h"
00066 #include "asterisk/sched.h"
00067 #include "asterisk/io.h"
00068 #include "asterisk/config.h"
00069 #include "asterisk/cli.h"
00070 #include "asterisk/translate.h"
00071 #include "asterisk/md5.h"
00072 #include "asterisk/cdr.h"
00073 #include "asterisk/crypto.h"
00074 #include "asterisk/acl.h"
00075 #include "asterisk/manager.h"
00076 #include "asterisk/callerid.h"
00077 #include "asterisk/app.h"
00078 #include "asterisk/astdb.h"
00079 #include "asterisk/musiconhold.h"
00080 #include "asterisk/features.h"
00081 #include "asterisk/utils.h"
00082 #include "asterisk/causes.h"
00083 #include "asterisk/localtime.h"
00084 #include "asterisk/dnsmgr.h"
00085 #include "asterisk/devicestate.h"
00086 #include "asterisk/netsock.h"
00087 #include "asterisk/stringfields.h"
00088 #include "asterisk/linkedlists.h"
00089 #include "asterisk/event.h"
00090 #include "asterisk/astobj2.h"
00091 #include "asterisk/timing.h"
00092 #include "asterisk/taskprocessor.h"
00093 #include "asterisk/test.h"
00094 #include "asterisk/data.h"
00095 #include "asterisk/netsock2.h"
00096
00097 #include "iax2.h"
00098 #include "iax2-parser.h"
00099 #include "iax2-provision.h"
00100 #include "jitterbuf.h"
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228
00229
00230
00231 #define SCHED_MULTITHREADED
00232
00233
00234
00235 #define DEBUG_SCHED_MULTITHREAD
00236
00237
00238 #ifdef SO_NO_CHECK
00239 static int nochecksums = 0;
00240 #endif
00241
00242 #define PTR_TO_CALLNO(a) ((unsigned short)(unsigned long)(a))
00243 #define CALLNO_TO_PTR(a) ((void *)(unsigned long)(a))
00244
00245 #define DEFAULT_THREAD_COUNT 10
00246 #define DEFAULT_MAX_THREAD_COUNT 100
00247 #define DEFAULT_RETRY_TIME 1000
00248 #define MEMORY_SIZE 100
00249 #define DEFAULT_DROP 3
00250
00251 #define DEBUG_SUPPORT
00252
00253 #define MIN_REUSE_TIME 60
00254
00255
00256 #define GAMMA (0.01)
00257
00258 static struct ast_codec_pref prefs;
00259
00260 static const char tdesc[] = "Inter Asterisk eXchange Driver (Ver 2)";
00261
00262
00263
00264
00265 #define MAX_TRUNK_MTU 1240
00266
00267 static int global_max_trunk_mtu;
00268 static int trunk_timed, trunk_untimed, trunk_maxmtu, trunk_nmaxmtu ;
00269
00270 #define DEFAULT_CONTEXT "default"
00271
00272 static char default_parkinglot[AST_MAX_CONTEXT];
00273
00274 static char language[MAX_LANGUAGE] = "";
00275 static char regcontext[AST_MAX_CONTEXT] = "";
00276
00277 static struct ast_event_sub *network_change_event_subscription;
00278 static int network_change_event_sched_id = -1;
00279
00280 static int maxauthreq = 3;
00281 static int max_retries = 4;
00282 static int ping_time = 21;
00283 static int lagrq_time = 10;
00284 static int maxjitterbuffer=1000;
00285 static int resyncthreshold=1000;
00286 static int maxjitterinterps=10;
00287 static int jittertargetextra = 40;
00288
00289 #define MAX_TRUNKDATA 640 * 200
00290
00291 static int trunkfreq = 20;
00292 static int trunkmaxsize = MAX_TRUNKDATA;
00293
00294 static int authdebug = 1;
00295 static int autokill = 0;
00296 static int iaxcompat = 0;
00297 static int last_authmethod = 0;
00298
00299 static int iaxdefaultdpcache=10 * 60;
00300
00301 static int iaxdefaulttimeout = 5;
00302
00303 static struct {
00304 unsigned int tos;
00305 unsigned int cos;
00306 } qos = { 0, 0 };
00307
00308 static int min_reg_expire;
00309 static int max_reg_expire;
00310
00311 static int srvlookup = 0;
00312
00313 static struct ast_timer *timer;
00314
00315 static struct ast_netsock_list *netsock;
00316 static struct ast_netsock_list *outsock;
00317 static int defaultsockfd = -1;
00318
00319 static int (*iax2_regfunk)(const char *username, int onoff) = NULL;
00320
00321
00322 #define IAX_CAPABILITY_FULLBANDWIDTH 0xFFFF
00323
00324 #define IAX_CAPABILITY_MEDBANDWIDTH (IAX_CAPABILITY_FULLBANDWIDTH & \
00325 ~AST_FORMAT_SLINEAR & \
00326 ~AST_FORMAT_SLINEAR16 & \
00327 ~AST_FORMAT_SIREN7 & \
00328 ~AST_FORMAT_SIREN14 & \
00329 ~AST_FORMAT_G719 & \
00330 ~AST_FORMAT_ULAW & \
00331 ~AST_FORMAT_ALAW & \
00332 ~AST_FORMAT_G722)
00333
00334 #define IAX_CAPABILITY_LOWBANDWIDTH (IAX_CAPABILITY_MEDBANDWIDTH & \
00335 ~AST_FORMAT_G726 & \
00336 ~AST_FORMAT_G726_AAL2 & \
00337 ~AST_FORMAT_ADPCM)
00338
00339 #define IAX_CAPABILITY_LOWFREE (IAX_CAPABILITY_LOWBANDWIDTH & \
00340 ~AST_FORMAT_G723_1)
00341
00342
00343 #define DEFAULT_MAXMS 2000
00344 #define DEFAULT_FREQ_OK 60 * 1000
00345 #define DEFAULT_FREQ_NOTOK 10 * 1000
00346
00347
00348 #define IAX_CALLENCRYPTED(pvt) \
00349 (ast_test_flag64(pvt, IAX_ENCRYPTED) && ast_test_flag64(pvt, IAX_KEYPOPULATED))
00350
00351 #define IAX_DEBUGDIGEST(msg, key) do { \
00352 int idx; \
00353 char digest[33] = ""; \
00354 \
00355 if (!iaxdebug) \
00356 break; \
00357 \
00358 for (idx = 0; idx < 16; idx++) \
00359 sprintf(digest + (idx << 1), "%2.2x", (unsigned char) key[idx]); \
00360 \
00361 ast_log(LOG_NOTICE, msg " IAX_COMMAND_RTKEY to rotate key to '%s'\n", digest); \
00362 } while(0)
00363
00364 static struct io_context *io;
00365 static struct ast_sched_thread *sched;
00366
00367 #define DONT_RESCHEDULE -2
00368
00369 static format_t iax2_capability = IAX_CAPABILITY_FULLBANDWIDTH;
00370
00371 static int iaxdebug = 0;
00372
00373 static int iaxtrunkdebug = 0;
00374
00375 static int test_losspct = 0;
00376 #ifdef IAXTESTS
00377 static int test_late = 0;
00378 static int test_resync = 0;
00379 static int test_jit = 0;
00380 static int test_jitpct = 0;
00381 #endif
00382
00383 static char accountcode[AST_MAX_ACCOUNT_CODE];
00384 static char mohinterpret[MAX_MUSICCLASS];
00385 static char mohsuggest[MAX_MUSICCLASS];
00386 static int amaflags = 0;
00387 static int adsi = 0;
00388 static int delayreject = 0;
00389 static int iax2_encryption = 0;
00390
00391 static struct ast_flags64 globalflags = { 0 };
00392
00393 static pthread_t netthreadid = AST_PTHREADT_NULL;
00394
00395 enum iax2_state {
00396 IAX_STATE_STARTED = (1 << 0),
00397 IAX_STATE_AUTHENTICATED = (1 << 1),
00398 IAX_STATE_TBD = (1 << 2),
00399 };
00400
00401 struct iax2_context {
00402 char context[AST_MAX_CONTEXT];
00403 struct iax2_context *next;
00404 };
00405
00406
00407 #define IAX_HASCALLERID (uint64_t)(1 << 0)
00408 #define IAX_DELME (uint64_t)(1 << 1)
00409 #define IAX_TEMPONLY (uint64_t)(1 << 2)
00410 #define IAX_TRUNK (uint64_t)(1 << 3)
00411 #define IAX_NOTRANSFER (uint64_t)(1 << 4)
00412 #define IAX_USEJITTERBUF (uint64_t)(1 << 5)
00413 #define IAX_DYNAMIC (uint64_t)(1 << 6)
00414 #define IAX_SENDANI (uint64_t)(1 << 7)
00415 #define IAX_RTSAVE_SYSNAME (uint64_t)(1 << 8)
00416 #define IAX_ALREADYGONE (uint64_t)(1 << 9)
00417 #define IAX_PROVISION (uint64_t)(1 << 10)
00418 #define IAX_QUELCH (uint64_t)(1 << 11)
00419 #define IAX_ENCRYPTED (uint64_t)(1 << 12)
00420 #define IAX_KEYPOPULATED (uint64_t)(1 << 13)
00421 #define IAX_CODEC_USER_FIRST (uint64_t)(1 << 14)
00422 #define IAX_CODEC_NOPREFS (uint64_t)(1 << 15)
00423 #define IAX_CODEC_NOCAP (uint64_t)(1 << 16)
00424 #define IAX_RTCACHEFRIENDS (uint64_t)(1 << 17)
00425 #define IAX_RTUPDATE (uint64_t)(1 << 18)
00426 #define IAX_RTAUTOCLEAR (uint64_t)(1 << 19)
00427 #define IAX_FORCEJITTERBUF (uint64_t)(1 << 20)
00428 #define IAX_RTIGNOREREGEXPIRE (uint64_t)(1 << 21)
00429 #define IAX_TRUNKTIMESTAMPS (uint64_t)(1 << 22)
00430 #define IAX_TRANSFERMEDIA (uint64_t)(1 << 23)
00431 #define IAX_MAXAUTHREQ (uint64_t)(1 << 24)
00432 #define IAX_DELAYPBXSTART (uint64_t)(1 << 25)
00433 #define IAX_ALLOWFWDOWNLOAD (uint64_t)(1 << 26)
00434 #define IAX_IMMEDIATE (uint64_t)(1 << 27)
00435 #define IAX_SENDCONNECTEDLINE (uint64_t)(1 << 28)
00436 #define IAX_RECVCONNECTEDLINE (uint64_t)(1 << 29)
00437 #define IAX_FORCE_ENCRYPT (uint64_t)(1 << 30)
00438 #define IAX_SHRINKCALLERID (uint64_t)(1 << 31)
00439 static int global_rtautoclear = 120;
00440
00441 static int reload_config(void);
00442
00443
00444
00445
00446 enum calltoken_peer_enum {
00447
00448 CALLTOKEN_DEFAULT = 0,
00449
00450 CALLTOKEN_YES = 1,
00451
00452
00453 CALLTOKEN_AUTO = 2,
00454
00455 CALLTOKEN_NO = 3,
00456 };
00457
00458 struct iax2_user {
00459 AST_DECLARE_STRING_FIELDS(
00460 AST_STRING_FIELD(name);
00461 AST_STRING_FIELD(secret);
00462 AST_STRING_FIELD(dbsecret);
00463 AST_STRING_FIELD(accountcode);
00464 AST_STRING_FIELD(mohinterpret);
00465 AST_STRING_FIELD(mohsuggest);
00466 AST_STRING_FIELD(inkeys);
00467 AST_STRING_FIELD(language);
00468 AST_STRING_FIELD(cid_num);
00469 AST_STRING_FIELD(cid_name);
00470 AST_STRING_FIELD(parkinglot);
00471 );
00472
00473 int authmethods;
00474 int encmethods;
00475 int amaflags;
00476 int adsi;
00477 uint64_t flags;
00478 format_t capability;
00479 int maxauthreq;
00480 int curauthreq;
00481 struct ast_codec_pref prefs;
00482 struct ast_ha *ha;
00483 struct iax2_context *contexts;
00484 struct ast_variable *vars;
00485 enum calltoken_peer_enum calltoken_required;
00486 };
00487
00488 struct iax2_peer {
00489 AST_DECLARE_STRING_FIELDS(
00490 AST_STRING_FIELD(name);
00491 AST_STRING_FIELD(username);
00492 AST_STRING_FIELD(secret);
00493 AST_STRING_FIELD(dbsecret);
00494 AST_STRING_FIELD(outkey);
00495
00496 AST_STRING_FIELD(regexten);
00497 AST_STRING_FIELD(context);
00498 AST_STRING_FIELD(peercontext);
00499 AST_STRING_FIELD(mailbox);
00500 AST_STRING_FIELD(mohinterpret);
00501 AST_STRING_FIELD(mohsuggest);
00502 AST_STRING_FIELD(inkeys);
00503
00504 AST_STRING_FIELD(cid_num);
00505 AST_STRING_FIELD(cid_name);
00506 AST_STRING_FIELD(zonetag);
00507 AST_STRING_FIELD(parkinglot);
00508 );
00509 struct ast_codec_pref prefs;
00510 struct ast_dnsmgr_entry *dnsmgr;
00511 struct ast_sockaddr addr;
00512 int formats;
00513 int sockfd;
00514 struct in_addr mask;
00515 int adsi;
00516 uint64_t flags;
00517
00518
00519 struct sockaddr_in defaddr;
00520 int authmethods;
00521 int encmethods;
00522
00523 int expire;
00524 int expiry;
00525 format_t capability;
00526
00527
00528 int callno;
00529 int pokeexpire;
00530 int lastms;
00531 int maxms;
00532
00533 int pokefreqok;
00534 int pokefreqnotok;
00535 int historicms;
00536 int smoothing;
00537 uint16_t maxcallno;
00538
00539 struct ast_event_sub *mwi_event_sub;
00540
00541 struct ast_ha *ha;
00542 enum calltoken_peer_enum calltoken_required;
00543 };
00544
00545 #define IAX2_TRUNK_PREFACE (sizeof(struct iax_frame) + sizeof(struct ast_iax2_meta_hdr) + sizeof(struct ast_iax2_meta_trunk_hdr))
00546
00547 struct iax2_trunk_peer {
00548 ast_mutex_t lock;
00549 int sockfd;
00550 struct sockaddr_in addr;
00551 struct timeval txtrunktime;
00552 struct timeval rxtrunktime;
00553 struct timeval lasttxtime;
00554 struct timeval trunkact;
00555 unsigned int lastsent;
00556
00557 unsigned char *trunkdata;
00558 unsigned int trunkdatalen;
00559 unsigned int trunkdataalloc;
00560 int trunkmaxmtu;
00561 int trunkerror;
00562 int calls;
00563 AST_LIST_ENTRY(iax2_trunk_peer) list;
00564 };
00565
00566 static AST_LIST_HEAD_STATIC(tpeers, iax2_trunk_peer);
00567
00568 struct iax_firmware {
00569 AST_LIST_ENTRY(iax_firmware) list;
00570 int fd;
00571 int mmaplen;
00572 int dead;
00573 struct ast_iax2_firmware_header *fwh;
00574 unsigned char *buf;
00575 };
00576
00577 enum iax_reg_state {
00578 REG_STATE_UNREGISTERED = 0,
00579 REG_STATE_REGSENT,
00580 REG_STATE_AUTHSENT,
00581 REG_STATE_REGISTERED,
00582 REG_STATE_REJECTED,
00583 REG_STATE_TIMEOUT,
00584 REG_STATE_NOAUTH
00585 };
00586
00587 enum iax_transfer_state {
00588 TRANSFER_NONE = 0,
00589 TRANSFER_BEGIN,
00590 TRANSFER_READY,
00591 TRANSFER_RELEASED,
00592 TRANSFER_PASSTHROUGH,
00593 TRANSFER_MBEGIN,
00594 TRANSFER_MREADY,
00595 TRANSFER_MRELEASED,
00596 TRANSFER_MPASSTHROUGH,
00597 TRANSFER_MEDIA,
00598 TRANSFER_MEDIAPASS
00599 };
00600
00601 struct iax2_registry {
00602 struct ast_sockaddr addr;
00603 char username[80];
00604 char secret[80];
00605 int expire;
00606 int refresh;
00607 enum iax_reg_state regstate;
00608 int messages;
00609 int callno;
00610 struct sockaddr_in us;
00611 struct ast_dnsmgr_entry *dnsmgr;
00612 AST_LIST_ENTRY(iax2_registry) entry;
00613 };
00614
00615 static AST_LIST_HEAD_STATIC(registrations, iax2_registry);
00616
00617
00618 #define MIN_RETRY_TIME 100
00619 #define MAX_RETRY_TIME 10000
00620
00621 #define MAX_JITTER_BUFFER 50
00622 #define MIN_JITTER_BUFFER 10
00623
00624 #define DEFAULT_TRUNKDATA 640 * 10
00625
00626 #define MAX_TIMESTAMP_SKEW 160
00627
00628
00629 #define TS_GAP_FOR_JB_RESYNC 5000
00630
00631
00632 #define MARK_IAX_SUBCLASS_TX 0x8000
00633
00634 static int iaxthreadcount = DEFAULT_THREAD_COUNT;
00635 static int iaxmaxthreadcount = DEFAULT_MAX_THREAD_COUNT;
00636 static int iaxdynamicthreadcount = 0;
00637 static int iaxdynamicthreadnum = 0;
00638 static int iaxactivethreadcount = 0;
00639
00640 struct iax_rr {
00641 int jitter;
00642 int losspct;
00643 int losscnt;
00644 int packets;
00645 int delay;
00646 int dropped;
00647 int ooo;
00648 };
00649
00650 struct iax2_pvt_ref;
00651
00652 struct chan_iax2_pvt {
00653
00654 int sockfd;
00655
00656 format_t voiceformat;
00657
00658 format_t videoformat;
00659
00660 format_t svoiceformat;
00661
00662 format_t svideoformat;
00663
00664 format_t capability;
00665
00666 unsigned int last;
00667
00668 unsigned int lastsent;
00669
00670 unsigned int lastvsent;
00671
00672 unsigned int nextpred;
00673
00674 int first_iax_message;
00675
00676 int last_iax_message;
00677
00678 unsigned int notsilenttx:1;
00679
00680 unsigned int pingtime;
00681
00682 int maxtime;
00683
00684 struct sockaddr_in addr;
00685
00686 struct ast_codec_pref prefs;
00687
00688 struct ast_codec_pref rprefs;
00689
00690 unsigned short callno;
00691
00692 struct callno_entry *callno_entry;
00693
00694 unsigned short peercallno;
00695
00696
00697
00698 format_t chosenformat;
00699
00700 format_t peerformat;
00701
00702 format_t peercapability;
00703
00704 struct timeval offset;
00705
00706 struct timeval rxcore;
00707
00708 jitterbuf *jb;
00709
00710 int jbid;
00711
00712 int lag;
00713
00714 int error;
00715
00716 struct ast_channel *owner;
00717
00718 struct ast_flags state;
00719
00720 int expiry;
00721
00722 unsigned char oseqno;
00723
00724 unsigned char rseqno;
00725
00726 unsigned char iseqno;
00727
00728 unsigned char aseqno;
00729
00730 AST_DECLARE_STRING_FIELDS(
00731
00732 AST_STRING_FIELD(peer);
00733
00734 AST_STRING_FIELD(context);
00735
00736 AST_STRING_FIELD(cid_num);
00737 AST_STRING_FIELD(cid_name);
00738
00739 AST_STRING_FIELD(ani);
00740
00741 AST_STRING_FIELD(dnid);
00742
00743 AST_STRING_FIELD(rdnis);
00744
00745 AST_STRING_FIELD(exten);
00746
00747 AST_STRING_FIELD(username);
00748
00749 AST_STRING_FIELD(secret);
00750
00751 AST_STRING_FIELD(challenge);
00752
00753 AST_STRING_FIELD(inkeys);
00754
00755 AST_STRING_FIELD(outkey);
00756
00757 AST_STRING_FIELD(language);
00758
00759 AST_STRING_FIELD(host);
00760
00761 AST_STRING_FIELD(dproot);
00762 AST_STRING_FIELD(accountcode);
00763 AST_STRING_FIELD(mohinterpret);
00764 AST_STRING_FIELD(mohsuggest);
00765
00766 AST_STRING_FIELD(osptoken);
00767
00768 AST_STRING_FIELD(parkinglot);
00769 );
00770
00771 int authrej;
00772
00773 int authmethods;
00774
00775 int encmethods;
00776
00777 ast_aes_encrypt_key ecx;
00778
00779 ast_aes_decrypt_key mydcx;
00780
00781 ast_aes_decrypt_key dcx;
00782
00783
00784 int keyrotateid;
00785
00786 unsigned char semirand[32];
00787
00788 struct iax2_registry *reg;
00789
00790 struct iax2_peer *peerpoke;
00791
00792 uint64_t flags;
00793 int adsi;
00794
00795
00796 enum iax_transfer_state transferring;
00797
00798 int transferid;
00799
00800 struct sockaddr_in transfer;
00801
00802 unsigned short transfercallno;
00803
00804 ast_aes_encrypt_key tdcx;
00805
00806
00807 int peeradsicpe;
00808
00809
00810 unsigned short bridgecallno;
00811
00812 int pingid;
00813 int lagid;
00814 int autoid;
00815 int authid;
00816 int authfail;
00817 int initid;
00818 int calling_ton;
00819 int calling_tns;
00820 int calling_pres;
00821 int amaflags;
00822 AST_LIST_HEAD_NOLOCK(, iax2_dpcache) dpentries;
00823
00824 struct ast_variable *vars;
00825
00826 struct ast_variable *iaxvars;
00827
00828 struct iax_rr remote_rr;
00829
00830 int min;
00831
00832 int frames_dropped;
00833
00834 int frames_received;
00835
00836 unsigned char calltoken_ie_len;
00837
00838 char hold_signaling;
00839
00840 AST_LIST_HEAD_NOLOCK(signaling_queue, signaling_queue_entry) signaling_queue;
00841 };
00842
00843 struct signaling_queue_entry {
00844 struct ast_frame f;
00845 AST_LIST_ENTRY(signaling_queue_entry) next;
00846 };
00847
00848
00849 static struct ao2_container *callno_pool;
00850
00851
00852 static struct ao2_container *callno_pool_trunk;
00853
00854 static const unsigned int CALLNO_POOL_BUCKETS = 2699;
00855
00856
00857
00858
00859
00860
00861
00862
00863
00864
00865 static AST_LIST_HEAD_NOLOCK(, iax_frame) frame_queue[IAX_MAX_CALLS + 1];
00866
00867 static struct ast_taskprocessor *transmit_processor;
00868
00869 static int randomcalltokendata;
00870
00871 static const time_t MAX_CALLTOKEN_DELAY = 10;
00872
00873
00874
00875
00876
00877
00878
00879
00880 #ifdef LOW_MEMORY
00881 #define MAX_PEER_BUCKETS 17
00882 #else
00883 #define MAX_PEER_BUCKETS 563
00884 #endif
00885 static struct ao2_container *peers;
00886
00887 #define MAX_USER_BUCKETS MAX_PEER_BUCKETS
00888 static struct ao2_container *users;
00889
00890
00891 static struct ao2_container *peercnts;
00892
00893
00894 static struct ao2_container *callno_limits;
00895
00896
00897 static struct ao2_container *calltoken_ignores;
00898
00899 static uint16_t DEFAULT_MAXCALLNO_LIMIT = 2048;
00900
00901 static uint16_t DEFAULT_MAXCALLNO_LIMIT_NONVAL = 8192;
00902
00903 static uint16_t global_maxcallno;
00904
00905
00906 static uint16_t global_maxcallno_nonval;
00907
00908 static uint16_t total_nonval_callno_used = 0;
00909
00910
00911
00912 struct peercnt {
00913
00914 unsigned long addr;
00915
00916 uint16_t cur;
00917
00918 uint16_t limit;
00919
00920
00921 unsigned char reg;
00922 };
00923
00924
00925 struct addr_range {
00926
00927 struct ast_ha ha;
00928
00929 uint16_t limit;
00930
00931 unsigned char delme;
00932 };
00933
00934 struct callno_entry {
00935
00936 uint16_t callno;
00937
00938 unsigned char validated;
00939 };
00940
00941 static AST_LIST_HEAD_STATIC(firmwares, iax_firmware);
00942
00943 enum {
00944
00945 CACHE_FLAG_EXISTS = (1 << 0),
00946
00947 CACHE_FLAG_NONEXISTENT = (1 << 1),
00948
00949 CACHE_FLAG_CANEXIST = (1 << 2),
00950
00951 CACHE_FLAG_PENDING = (1 << 3),
00952
00953 CACHE_FLAG_TIMEOUT = (1 << 4),
00954
00955 CACHE_FLAG_TRANSMITTED = (1 << 5),
00956
00957 CACHE_FLAG_UNKNOWN = (1 << 6),
00958
00959 CACHE_FLAG_MATCHMORE = (1 << 7),
00960 };
00961
00962 struct iax2_dpcache {
00963 char peercontext[AST_MAX_CONTEXT];
00964 char exten[AST_MAX_EXTENSION];
00965 struct timeval orig;
00966 struct timeval expiry;
00967 int flags;
00968 unsigned short callno;
00969 int waiters[256];
00970 AST_LIST_ENTRY(iax2_dpcache) cache_list;
00971 AST_LIST_ENTRY(iax2_dpcache) peer_list;
00972 };
00973
00974 static AST_LIST_HEAD_STATIC(dpcache, iax2_dpcache);
00975
00976 static void reg_source_db(struct iax2_peer *p);
00977 static struct iax2_peer *realtime_peer(const char *peername, struct sockaddr_in *sin);
00978 static struct iax2_user *realtime_user(const char *username, struct sockaddr_in *sin);
00979
00980 static int ast_cli_netstats(struct mansession *s, int fd, int limit_fmt);
00981 static char *complete_iax2_peers(const char *line, const char *word, int pos, int state, uint64_t flags);
00982 static char *complete_iax2_unregister(const char *line, const char *word, int pos, int state);
00983
00984 enum iax2_thread_iostate {
00985 IAX_IOSTATE_IDLE,
00986 IAX_IOSTATE_READY,
00987 IAX_IOSTATE_PROCESSING,
00988 IAX_IOSTATE_SCHEDREADY,
00989 };
00990
00991 enum iax2_thread_type {
00992 IAX_THREAD_TYPE_POOL,
00993 IAX_THREAD_TYPE_DYNAMIC,
00994 };
00995
00996 struct iax2_pkt_buf {
00997 AST_LIST_ENTRY(iax2_pkt_buf) entry;
00998 size_t len;
00999 unsigned char buf[1];
01000 };
01001
01002 struct iax2_thread {
01003 AST_LIST_ENTRY(iax2_thread) list;
01004 enum iax2_thread_type type;
01005 enum iax2_thread_iostate iostate;
01006 #ifdef SCHED_MULTITHREADED
01007 void (*schedfunc)(const void *);
01008 const void *scheddata;
01009 #endif
01010 #ifdef DEBUG_SCHED_MULTITHREAD
01011 char curfunc[80];
01012 #endif
01013 int actions;
01014 pthread_t threadid;
01015 int threadnum;
01016 struct sockaddr_in iosin;
01017 unsigned char readbuf[4096];
01018 unsigned char *buf;
01019 ssize_t buf_len;
01020 size_t buf_size;
01021 int iofd;
01022 time_t checktime;
01023 ast_mutex_t lock;
01024 ast_cond_t cond;
01025 ast_mutex_t init_lock;
01026 ast_cond_t init_cond;
01027
01028
01029
01030
01031 struct {
01032 unsigned short callno;
01033 struct sockaddr_in sin;
01034 unsigned char type;
01035 unsigned char csub;
01036 } ffinfo;
01037
01038
01039
01040 AST_LIST_HEAD_NOLOCK(, iax2_pkt_buf) full_frames;
01041 unsigned char stop;
01042 };
01043
01044
01045 static AST_LIST_HEAD_STATIC(idle_list, iax2_thread);
01046 static AST_LIST_HEAD_STATIC(active_list, iax2_thread);
01047 static AST_LIST_HEAD_STATIC(dynamic_list, iax2_thread);
01048
01049 static void *iax2_process_thread(void *data);
01050 static void iax2_destroy(int callno);
01051
01052 static void signal_condition(ast_mutex_t *lock, ast_cond_t *cond)
01053 {
01054 ast_mutex_lock(lock);
01055 ast_cond_signal(cond);
01056 ast_mutex_unlock(lock);
01057 }
01058
01059
01060
01061
01062
01063
01064
01065
01066
01067 static struct chan_iax2_pvt *iaxs[IAX_MAX_CALLS + 1];
01068
01069
01070
01071
01072
01073
01074
01075
01076
01077
01078 static struct ao2_container *iax_peercallno_pvts;
01079
01080
01081
01082
01083
01084
01085
01086
01087 static ast_mutex_t iaxsl[ARRAY_LEN(iaxs)];
01088
01089
01090
01091
01092
01093
01094 static struct ao2_container *iax_transfercallno_pvts;
01095
01096
01097
01098 #define TRUNK_CALL_START IAX_MAX_CALLS / 2
01099
01100
01101 static struct sockaddr_in debugaddr;
01102
01103 static void iax_outputframe(struct iax_frame *f, struct ast_iax2_full_hdr *fhi, int rx, struct sockaddr_in *sin, int datalen)
01104 {
01105 if (iaxdebug ||
01106 (sin && debugaddr.sin_addr.s_addr &&
01107 (!ntohs(debugaddr.sin_port) ||
01108 debugaddr.sin_port == sin->sin_port) &&
01109 debugaddr.sin_addr.s_addr == sin->sin_addr.s_addr)) {
01110 if (iaxdebug) {
01111 iax_showframe(f, fhi, rx, sin, datalen);
01112 } else {
01113 iaxdebug = 1;
01114 iax_showframe(f, fhi, rx, sin, datalen);
01115 iaxdebug = 0;
01116 }
01117 }
01118 }
01119
01120 static void iax_debug_output(const char *data)
01121 {
01122 if (iaxdebug)
01123 ast_verbose("%s", data);
01124 }
01125
01126 static void iax_error_output(const char *data)
01127 {
01128 ast_log(LOG_WARNING, "%s", data);
01129 }
01130
01131 static void __attribute__((format(printf, 1, 2))) jb_error_output(const char *fmt, ...)
01132 {
01133 va_list args;
01134 char buf[1024];
01135
01136 va_start(args, fmt);
01137 vsnprintf(buf, sizeof(buf), fmt, args);
01138 va_end(args);
01139
01140 ast_log(LOG_ERROR, "%s", buf);
01141 }
01142
01143 static void __attribute__((format(printf, 1, 2))) jb_warning_output(const char *fmt, ...)
01144 {
01145 va_list args;
01146 char buf[1024];
01147
01148 va_start(args, fmt);
01149 vsnprintf(buf, sizeof(buf), fmt, args);
01150 va_end(args);
01151
01152 ast_log(LOG_WARNING, "%s", buf);
01153 }
01154
01155 static void __attribute__((format(printf, 1, 2))) jb_debug_output(const char *fmt, ...)
01156 {
01157 va_list args;
01158 char buf[1024];
01159
01160 va_start(args, fmt);
01161 vsnprintf(buf, sizeof(buf), fmt, args);
01162 va_end(args);
01163
01164 ast_verbose("%s", buf);
01165 }
01166
01167 static enum ast_bridge_result iax2_bridge(struct ast_channel *c0, struct ast_channel *c1, int flags, struct ast_frame **fo, struct ast_channel **rc, int timeoutms);
01168 static int expire_registry(const void *data);
01169 static int iax2_answer(struct ast_channel *c);
01170 static int iax2_call(struct ast_channel *c, char *dest, int timeout);
01171 static int iax2_devicestate(void *data);
01172 static int iax2_digit_begin(struct ast_channel *c, char digit);
01173 static int iax2_digit_end(struct ast_channel *c, char digit, unsigned int duration);
01174 static int iax2_do_register(struct iax2_registry *reg);
01175 static int iax2_fixup(struct ast_channel *oldchannel, struct ast_channel *newchan);
01176 static int iax2_hangup(struct ast_channel *c);
01177 static int iax2_indicate(struct ast_channel *c, int condition, const void *data, size_t datalen);
01178 static int iax2_poke_peer(struct iax2_peer *peer, int heldcall);
01179 static int iax2_provision(struct sockaddr_in *end, int sockfd, const char *dest, const char *template, int force);
01180 static int iax2_send(struct chan_iax2_pvt *pvt, struct ast_frame *f, unsigned int ts, int seqno, int now, int transfer, int final);
01181 static int iax2_sendhtml(struct ast_channel *c, int subclass, const char *data, int datalen);
01182 static int iax2_sendimage(struct ast_channel *c, struct ast_frame *img);
01183 static int iax2_sendtext(struct ast_channel *c, const char *text);
01184 static int iax2_setoption(struct ast_channel *c, int option, void *data, int datalen);
01185 static int iax2_queryoption(struct ast_channel *c, int option, void *data, int *datalen);
01186 static int iax2_transfer(struct ast_channel *c, const char *dest);
01187 static int iax2_write(struct ast_channel *c, struct ast_frame *f);
01188 static int iax2_sched_add(struct ast_sched_thread *st, int when, ast_sched_cb callback, const void *data);
01189
01190 static int send_trunk(struct iax2_trunk_peer *tpeer, struct timeval *now);
01191 static int send_command(struct chan_iax2_pvt *, char, int, unsigned int, const unsigned char *, int, int);
01192 static int send_command_final(struct chan_iax2_pvt *, char, int, unsigned int, const unsigned char *, int, int);
01193 static int send_command_immediate(struct chan_iax2_pvt *, char, int, unsigned int, const unsigned char *, int, int);
01194 static int send_command_locked(unsigned short callno, char, int, unsigned int, const unsigned char *, int, int);
01195 static int send_command_transfer(struct chan_iax2_pvt *, char, int, unsigned int, const unsigned char *, int);
01196 static struct ast_channel *iax2_request(const char *type, format_t format, const struct ast_channel *requestor, void *data, int *cause);
01197 static struct ast_frame *iax2_read(struct ast_channel *c);
01198 static struct iax2_peer *build_peer(const char *name, struct ast_variable *v, struct ast_variable *alt, int temponly);
01199 static struct iax2_user *build_user(const char *name, struct ast_variable *v, struct ast_variable *alt, int temponly);
01200 static void realtime_update_peer(const char *peername, struct ast_sockaddr *sockaddr, time_t regtime);
01201 static void *iax2_dup_variable_datastore(void *);
01202 static void prune_peers(void);
01203 static void prune_users(void);
01204 static void iax2_free_variable_datastore(void *);
01205
01206 static int acf_channel_read(struct ast_channel *chan, const char *funcname, char *preparse, char *buf, size_t buflen);
01207 static int decode_frame(ast_aes_decrypt_key *dcx, struct ast_iax2_full_hdr *fh, struct ast_frame *f, int *datalen);
01208 static int encrypt_frame(ast_aes_encrypt_key *ecx, struct ast_iax2_full_hdr *fh, unsigned char *poo, int *datalen);
01209 static void build_ecx_key(const unsigned char *digest, struct chan_iax2_pvt *pvt);
01210 static void build_rand_pad(unsigned char *buf, ssize_t len);
01211 static struct callno_entry *get_unused_callno(int trunk, int validated);
01212 static int replace_callno(const void *obj);
01213 static void sched_delay_remove(struct sockaddr_in *sin, struct callno_entry *callno_entry);
01214 static void network_change_event_cb(const struct ast_event *, void *);
01215
01216 static const struct ast_channel_tech iax2_tech = {
01217 .type = "IAX2",
01218 .description = tdesc,
01219 .capabilities = IAX_CAPABILITY_FULLBANDWIDTH,
01220 .properties = AST_CHAN_TP_WANTSJITTER,
01221 .requester = iax2_request,
01222 .devicestate = iax2_devicestate,
01223 .send_digit_begin = iax2_digit_begin,
01224 .send_digit_end = iax2_digit_end,
01225 .send_text = iax2_sendtext,
01226 .send_image = iax2_sendimage,
01227 .send_html = iax2_sendhtml,
01228 .call = iax2_call,
01229 .hangup = iax2_hangup,
01230 .answer = iax2_answer,
01231 .read = iax2_read,
01232 .write = iax2_write,
01233 .write_video = iax2_write,
01234 .indicate = iax2_indicate,
01235 .setoption = iax2_setoption,
01236 .queryoption = iax2_queryoption,
01237 .bridge = iax2_bridge,
01238 .transfer = iax2_transfer,
01239 .fixup = iax2_fixup,
01240 .func_channel_read = acf_channel_read,
01241 };
01242
01243
01244
01245
01246
01247
01248
01249
01250
01251
01252
01253
01254
01255
01256
01257
01258
01259
01260 static void iax2_lock_owner(int callno)
01261 {
01262 for (;;) {
01263 if (!iaxs[callno] || !iaxs[callno]->owner) {
01264
01265 break;
01266 }
01267 if (!ast_channel_trylock(iaxs[callno]->owner)) {
01268
01269 break;
01270 }
01271
01272 DEADLOCK_AVOIDANCE(&iaxsl[callno]);
01273 }
01274 }
01275
01276 static void mwi_event_cb(const struct ast_event *event, void *userdata)
01277 {
01278
01279
01280
01281 }
01282
01283 static void network_change_event_subscribe(void)
01284 {
01285 if (!network_change_event_subscription) {
01286 network_change_event_subscription = ast_event_subscribe(AST_EVENT_NETWORK_CHANGE,
01287 network_change_event_cb, "IAX2 Network Change", NULL, AST_EVENT_IE_END);
01288 }
01289 }
01290
01291 static void network_change_event_unsubscribe(void)
01292 {
01293 if (network_change_event_subscription) {
01294 network_change_event_subscription = ast_event_unsubscribe(network_change_event_subscription);
01295 }
01296 }
01297
01298 static int network_change_event_sched_cb(const void *data)
01299 {
01300 struct iax2_registry *reg;
01301 network_change_event_sched_id = -1;
01302 AST_LIST_LOCK(®istrations);
01303 AST_LIST_TRAVERSE(®istrations, reg, entry) {
01304 iax2_do_register(reg);
01305 }
01306 AST_LIST_UNLOCK(®istrations);
01307
01308 return 0;
01309 }
01310
01311 static void network_change_event_cb(const struct ast_event *event, void *userdata)
01312 {
01313 ast_debug(1, "IAX, got a network change event, renewing all IAX registrations.\n");
01314 if (network_change_event_sched_id == -1) {
01315 network_change_event_sched_id = iax2_sched_add(sched, 1000, network_change_event_sched_cb, NULL);
01316 }
01317
01318 }
01319
01320
01321
01322
01323 static void iax2_ami_channelupdate(struct chan_iax2_pvt *pvt)
01324 {
01325 manager_event(EVENT_FLAG_SYSTEM, "ChannelUpdate",
01326 "Channel: %s\r\nChanneltype: IAX2\r\nIAX2-callno-local: %d\r\nIAX2-callno-remote: %d\r\nIAX2-peer: %s\r\n",
01327 pvt->owner ? pvt->owner->name : "",
01328 pvt->callno, pvt->peercallno, pvt->peer ? pvt->peer : "");
01329 }
01330
01331 static const struct ast_datastore_info iax2_variable_datastore_info = {
01332 .type = "IAX2_VARIABLE",
01333 .duplicate = iax2_dup_variable_datastore,
01334 .destroy = iax2_free_variable_datastore,
01335 };
01336
01337 static void *iax2_dup_variable_datastore(void *old)
01338 {
01339 AST_LIST_HEAD(, ast_var_t) *oldlist = old, *newlist;
01340 struct ast_var_t *oldvar, *newvar;
01341
01342 newlist = ast_calloc(sizeof(*newlist), 1);
01343 if (!newlist) {
01344 ast_log(LOG_ERROR, "Unable to duplicate iax2 variables\n");
01345 return NULL;
01346 }
01347
01348 AST_LIST_HEAD_INIT(newlist);
01349 AST_LIST_LOCK(oldlist);
01350 AST_LIST_TRAVERSE(oldlist, oldvar, entries) {
01351 newvar = ast_var_assign(ast_var_name(oldvar), ast_var_value(oldvar));
01352 if (newvar)
01353 AST_LIST_INSERT_TAIL(newlist, newvar, entries);
01354 else
01355 ast_log(LOG_ERROR, "Unable to duplicate iax2 variable '%s'\n", ast_var_name(oldvar));
01356 }
01357 AST_LIST_UNLOCK(oldlist);
01358 return newlist;
01359 }
01360
01361 static void iax2_free_variable_datastore(void *old)
01362 {
01363 AST_LIST_HEAD(, ast_var_t) *oldlist = old;
01364 struct ast_var_t *oldvar;
01365
01366 AST_LIST_LOCK(oldlist);
01367 while ((oldvar = AST_LIST_REMOVE_HEAD(oldlist, entries))) {
01368 ast_free(oldvar);
01369 }
01370 AST_LIST_UNLOCK(oldlist);
01371 AST_LIST_HEAD_DESTROY(oldlist);
01372 ast_free(oldlist);
01373 }
01374
01375
01376
01377
01378
01379 static void insert_idle_thread(struct iax2_thread *thread)
01380 {
01381 if (thread->type == IAX_THREAD_TYPE_DYNAMIC) {
01382 AST_LIST_LOCK(&dynamic_list);
01383 AST_LIST_INSERT_TAIL(&dynamic_list, thread, list);
01384 AST_LIST_UNLOCK(&dynamic_list);
01385 } else {
01386 AST_LIST_LOCK(&idle_list);
01387 AST_LIST_INSERT_TAIL(&idle_list, thread, list);
01388 AST_LIST_UNLOCK(&idle_list);
01389 }
01390
01391 return;
01392 }
01393
01394 static struct iax2_thread *find_idle_thread(void)
01395 {
01396 struct iax2_thread *thread = NULL;
01397
01398
01399 AST_LIST_LOCK(&idle_list);
01400 thread = AST_LIST_REMOVE_HEAD(&idle_list, list);
01401 AST_LIST_UNLOCK(&idle_list);
01402
01403
01404 if (thread) {
01405 memset(&thread->ffinfo, 0, sizeof(thread->ffinfo));
01406 return thread;
01407 }
01408
01409
01410 AST_LIST_LOCK(&dynamic_list);
01411 thread = AST_LIST_REMOVE_HEAD(&dynamic_list, list);
01412 AST_LIST_UNLOCK(&dynamic_list);
01413
01414
01415 if (thread) {
01416 memset(&thread->ffinfo, 0, sizeof(thread->ffinfo));
01417 return thread;
01418 }
01419
01420
01421 if (iaxdynamicthreadcount >= iaxmaxthreadcount || !(thread = ast_calloc(1, sizeof(*thread))))
01422 return NULL;
01423
01424
01425 ast_atomic_fetchadd_int(&iaxdynamicthreadcount, 1);
01426 thread->threadnum = ast_atomic_fetchadd_int(&iaxdynamicthreadnum, 1);
01427 thread->type = IAX_THREAD_TYPE_DYNAMIC;
01428
01429
01430 ast_mutex_init(&thread->lock);
01431 ast_cond_init(&thread->cond, NULL);
01432 ast_mutex_init(&thread->init_lock);
01433 ast_cond_init(&thread->init_cond, NULL);
01434 ast_mutex_lock(&thread->init_lock);
01435
01436
01437 if (ast_pthread_create_background(&thread->threadid, NULL, iax2_process_thread, thread)) {
01438 ast_cond_destroy(&thread->cond);
01439 ast_mutex_destroy(&thread->lock);
01440 ast_mutex_unlock(&thread->init_lock);
01441 ast_cond_destroy(&thread->init_cond);
01442 ast_mutex_destroy(&thread->init_lock);
01443 ast_free(thread);
01444 return NULL;
01445 }
01446
01447
01448
01449 memset(&thread->ffinfo, 0, sizeof(thread->ffinfo));
01450
01451
01452 ast_cond_wait(&thread->init_cond, &thread->init_lock);
01453
01454
01455 ast_mutex_unlock(&thread->init_lock);
01456
01457 return thread;
01458 }
01459
01460 #ifdef SCHED_MULTITHREADED
01461 static int __schedule_action(void (*func)(const void *data), const void *data, const char *funcname)
01462 {
01463 struct iax2_thread *thread = NULL;
01464 static time_t lasterror;
01465 static time_t t;
01466
01467 thread = find_idle_thread();
01468
01469 if (thread != NULL) {
01470 thread->schedfunc = func;
01471 thread->scheddata = data;
01472 thread->iostate = IAX_IOSTATE_SCHEDREADY;
01473 #ifdef DEBUG_SCHED_MULTITHREAD
01474 ast_copy_string(thread->curfunc, funcname, sizeof(thread->curfunc));
01475 #endif
01476 signal_condition(&thread->lock, &thread->cond);
01477 return 0;
01478 }
01479 time(&t);
01480 if (t != lasterror)
01481 ast_debug(1, "Out of idle IAX2 threads for scheduling!\n");
01482 lasterror = t;
01483
01484 return -1;
01485 }
01486 #define schedule_action(func, data) __schedule_action(func, data, __PRETTY_FUNCTION__)
01487 #endif
01488
01489 static int iax2_sched_replace(int id, struct ast_sched_thread *st, int when,
01490 ast_sched_cb callback, const void *data)
01491 {
01492 ast_sched_thread_del(st, id);
01493
01494 return ast_sched_thread_add(st, when, callback, data);
01495 }
01496
01497 static int iax2_sched_add(struct ast_sched_thread *st, int when,
01498 ast_sched_cb callback, const void *data)
01499 {
01500 return ast_sched_thread_add(st, when, callback, data);
01501 }
01502
01503 static int send_ping(const void *data);
01504
01505 static void __send_ping(const void *data)
01506 {
01507 int callno = (long) data;
01508
01509 ast_mutex_lock(&iaxsl[callno]);
01510
01511 if (iaxs[callno]) {
01512 if (iaxs[callno]->peercallno) {
01513 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_PING, 0, NULL, 0, -1);
01514 if (iaxs[callno]->pingid != DONT_RESCHEDULE) {
01515 iaxs[callno]->pingid = iax2_sched_add(sched, ping_time * 1000, send_ping, data);
01516 }
01517 }
01518 } else {
01519 ast_debug(1, "I was supposed to send a PING with callno %d, but no such call exists.\n", callno);
01520 }
01521
01522 ast_mutex_unlock(&iaxsl[callno]);
01523 }
01524
01525 static int send_ping(const void *data)
01526 {
01527 int callno = (long) data;
01528 ast_mutex_lock(&iaxsl[callno]);
01529 if (iaxs[callno] && iaxs[callno]->pingid != DONT_RESCHEDULE) {
01530 iaxs[callno]->pingid = -1;
01531 }
01532 ast_mutex_unlock(&iaxsl[callno]);
01533
01534 #ifdef SCHED_MULTITHREADED
01535 if (schedule_action(__send_ping, data))
01536 #endif
01537 __send_ping(data);
01538
01539 return 0;
01540 }
01541
01542 static void encmethods_to_str(int e, struct ast_str *buf)
01543 {
01544 ast_str_set(&buf, 0, "(");
01545 if (e & IAX_ENCRYPT_AES128) {
01546 ast_str_append(&buf, 0, "aes128");
01547 }
01548 if (e & IAX_ENCRYPT_KEYROTATE) {
01549 ast_str_append(&buf, 0, ",keyrotate");
01550 }
01551 if (ast_str_strlen(buf) > 1) {
01552 ast_str_append(&buf, 0, ")");
01553 } else {
01554 ast_str_set(&buf, 0, "No");
01555 }
01556 }
01557
01558 static int get_encrypt_methods(const char *s)
01559 {
01560 int e;
01561 if (!strcasecmp(s, "aes128"))
01562 e = IAX_ENCRYPT_AES128 | IAX_ENCRYPT_KEYROTATE;
01563 else if (ast_true(s))
01564 e = IAX_ENCRYPT_AES128 | IAX_ENCRYPT_KEYROTATE;
01565 else
01566 e = 0;
01567 return e;
01568 }
01569
01570 static int send_lagrq(const void *data);
01571
01572 static void __send_lagrq(const void *data)
01573 {
01574 int callno = (long) data;
01575
01576 ast_mutex_lock(&iaxsl[callno]);
01577
01578 if (iaxs[callno]) {
01579 if (iaxs[callno]->peercallno) {
01580 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_LAGRQ, 0, NULL, 0, -1);
01581 if (iaxs[callno]->lagid != DONT_RESCHEDULE) {
01582 iaxs[callno]->lagid = iax2_sched_add(sched, lagrq_time * 1000, send_lagrq, data);
01583 }
01584 }
01585 } else {
01586 ast_debug(1, "I was supposed to send a LAGRQ with callno %d, but no such call exists.\n", callno);
01587 }
01588
01589 ast_mutex_unlock(&iaxsl[callno]);
01590 }
01591
01592 static int send_lagrq(const void *data)
01593 {
01594 int callno = (long) data;
01595 ast_mutex_lock(&iaxsl[callno]);
01596 if (iaxs[callno] && iaxs[callno]->lagid != DONT_RESCHEDULE) {
01597 iaxs[callno]->lagid = -1;
01598 }
01599 ast_mutex_unlock(&iaxsl[callno]);
01600
01601 #ifdef SCHED_MULTITHREADED
01602 if (schedule_action(__send_lagrq, data))
01603 #endif
01604 __send_lagrq(data);
01605 return 0;
01606 }
01607
01608 static unsigned char compress_subclass(format_t subclass)
01609 {
01610 int x;
01611 int power=-1;
01612
01613 if (subclass < IAX_FLAG_SC_LOG)
01614 return subclass;
01615
01616 for (x = 0; x < IAX_MAX_SHIFT; x++) {
01617 if (subclass & (1LL << x)) {
01618 if (power > -1) {
01619 ast_log(LOG_WARNING, "Can't compress subclass %lld\n", (long long) subclass);
01620 return 0;
01621 } else
01622 power = x;
01623 }
01624 }
01625 return power | IAX_FLAG_SC_LOG;
01626 }
01627
01628 static format_t uncompress_subclass(unsigned char csub)
01629 {
01630
01631 if (csub & IAX_FLAG_SC_LOG) {
01632
01633 if (csub == 0xff)
01634 return -1;
01635 else
01636 return 1LL << (csub & ~IAX_FLAG_SC_LOG & IAX_MAX_SHIFT);
01637 }
01638 else
01639 return csub;
01640 }
01641
01642
01643
01644
01645 static int peer_hash_cb(const void *obj, const int flags)
01646 {
01647 const struct iax2_peer *peer = obj;
01648
01649 return ast_str_hash(peer->name);
01650 }
01651
01652
01653
01654
01655 static int peer_cmp_cb(void *obj, void *arg, int flags)
01656 {
01657 struct iax2_peer *peer = obj, *peer2 = arg;
01658
01659 return !strcmp(peer->name, peer2->name) ? CMP_MATCH | CMP_STOP : 0;
01660 }
01661
01662
01663
01664
01665 static int user_hash_cb(const void *obj, const int flags)
01666 {
01667 const struct iax2_user *user = obj;
01668
01669 return ast_str_hash(user->name);
01670 }
01671
01672
01673
01674
01675 static int user_cmp_cb(void *obj, void *arg, int flags)
01676 {
01677 struct iax2_user *user = obj, *user2 = arg;
01678
01679 return !strcmp(user->name, user2->name) ? CMP_MATCH | CMP_STOP : 0;
01680 }
01681
01682
01683
01684
01685
01686 static struct iax2_peer *find_peer(const char *name, int realtime)
01687 {
01688 struct iax2_peer *peer = NULL;
01689 struct iax2_peer tmp_peer = {
01690 .name = name,
01691 };
01692
01693 peer = ao2_find(peers, &tmp_peer, OBJ_POINTER);
01694
01695
01696 if(!peer && realtime)
01697 peer = realtime_peer(name, NULL);
01698
01699 return peer;
01700 }
01701
01702 static struct iax2_peer *peer_ref(struct iax2_peer *peer)
01703 {
01704 ao2_ref(peer, +1);
01705 return peer;
01706 }
01707
01708 static inline struct iax2_peer *peer_unref(struct iax2_peer *peer)
01709 {
01710 ao2_ref(peer, -1);
01711 return NULL;
01712 }
01713
01714 static struct iax2_user *find_user(const char *name)
01715 {
01716 struct iax2_user tmp_user = {
01717 .name = name,
01718 };
01719
01720 return ao2_find(users, &tmp_user, OBJ_POINTER);
01721 }
01722 static inline struct iax2_user *user_ref(struct iax2_user *user)
01723 {
01724 ao2_ref(user, +1);
01725 return user;
01726 }
01727
01728 static inline struct iax2_user *user_unref(struct iax2_user *user)
01729 {
01730 ao2_ref(user, -1);
01731 return NULL;
01732 }
01733
01734 static int iax2_getpeername(struct sockaddr_in sin, char *host, int len)
01735 {
01736 struct iax2_peer *peer = NULL;
01737 int res = 0;
01738 struct ao2_iterator i;
01739
01740 i = ao2_iterator_init(peers, 0);
01741 while ((peer = ao2_iterator_next(&i))) {
01742 struct sockaddr_in peer_addr;
01743
01744 ast_sockaddr_to_sin(&peer->addr, &peer_addr);
01745
01746 if ((peer_addr.sin_addr.s_addr == sin.sin_addr.s_addr) &&
01747 (peer_addr.sin_port == sin.sin_port)) {
01748 ast_copy_string(host, peer->name, len);
01749 peer_unref(peer);
01750 res = 1;
01751 break;
01752 }
01753 peer_unref(peer);
01754 }
01755 ao2_iterator_destroy(&i);
01756
01757 if (!peer) {
01758 peer = realtime_peer(NULL, &sin);
01759 if (peer) {
01760 ast_copy_string(host, peer->name, len);
01761 peer_unref(peer);
01762 res = 1;
01763 }
01764 }
01765
01766 return res;
01767 }
01768
01769
01770
01771 static void iax2_destroy_helper(struct chan_iax2_pvt *pvt)
01772 {
01773
01774 if (ast_test_flag64(pvt, IAX_MAXAUTHREQ)) {
01775 struct iax2_user *user;
01776 struct iax2_user tmp_user = {
01777 .name = pvt->username,
01778 };
01779
01780 user = ao2_find(users, &tmp_user, OBJ_POINTER);
01781 if (user) {
01782 ast_atomic_fetchadd_int(&user->curauthreq, -1);
01783 user_unref(user);
01784 }
01785
01786 ast_clear_flag64(pvt, IAX_MAXAUTHREQ);
01787 }
01788
01789 AST_SCHED_DEL_SPINLOCK(ast_sched_thread_get_context(sched), pvt->pingid, &iaxsl[pvt->callno]);
01790 pvt->pingid = DONT_RESCHEDULE;
01791 AST_SCHED_DEL_SPINLOCK(ast_sched_thread_get_context(sched), pvt->lagid, &iaxsl[pvt->callno]);
01792 pvt->lagid = DONT_RESCHEDULE;
01793 ast_sched_thread_del(sched, pvt->autoid);
01794 ast_sched_thread_del(sched, pvt->authid);
01795 ast_sched_thread_del(sched, pvt->initid);
01796 ast_sched_thread_del(sched, pvt->jbid);
01797 ast_sched_thread_del(sched, pvt->keyrotateid);
01798 }
01799
01800 static void iax2_frame_free(struct iax_frame *fr)
01801 {
01802 ast_sched_thread_del(sched, fr->retrans);
01803 iax_frame_free(fr);
01804 }
01805
01806 static int scheduled_destroy(const void *vid)
01807 {
01808 unsigned short callno = PTR_TO_CALLNO(vid);
01809 ast_mutex_lock(&iaxsl[callno]);
01810 if (iaxs[callno]) {
01811 if (option_debug) {
01812 ast_log(LOG_DEBUG, "Really destroying %d now...\n", callno);
01813 }
01814 iax2_destroy(callno);
01815 }
01816 ast_mutex_unlock(&iaxsl[callno]);
01817 return 0;
01818 }
01819
01820 static void free_signaling_queue_entry(struct signaling_queue_entry *s)
01821 {
01822 if (s->f.datalen) {
01823 ast_free(s->f.data.ptr);
01824 }
01825 ast_free(s);
01826 }
01827
01828
01829
01830 static void send_signaling(struct chan_iax2_pvt *pvt)
01831 {
01832 struct signaling_queue_entry *s = NULL;
01833
01834 while ((s = AST_LIST_REMOVE_HEAD(&pvt->signaling_queue, next))) {
01835 iax2_send(pvt, &s->f, 0, -1, 0, 0, 0);
01836 free_signaling_queue_entry(s);
01837 }
01838 pvt->hold_signaling = 0;
01839 }
01840
01841
01842
01843 static int queue_signalling(struct chan_iax2_pvt *pvt, struct ast_frame *f)
01844 {
01845 struct signaling_queue_entry *qe;
01846
01847 if (f->frametype == AST_FRAME_IAX || !pvt->hold_signaling) {
01848 return 1;
01849 } else if (!(qe = ast_calloc(1, sizeof(struct signaling_queue_entry)))) {
01850 return -1;
01851 }
01852
01853
01854 qe->f = *f;
01855 if (qe->f.datalen) {
01856
01857 if (!(qe->f.data.ptr = ast_malloc(qe->f.datalen))) {
01858 free_signaling_queue_entry(qe);
01859 return -1;
01860 }
01861 memcpy(qe->f.data.ptr, f->data.ptr, qe->f.datalen);
01862 }
01863 AST_LIST_INSERT_TAIL(&pvt->signaling_queue, qe, next);
01864
01865 return 0;
01866 }
01867
01868 static void pvt_destructor(void *obj)
01869 {
01870 struct chan_iax2_pvt *pvt = obj;
01871 struct iax_frame *cur = NULL;
01872 struct signaling_queue_entry *s = NULL;
01873
01874 ast_mutex_lock(&iaxsl[pvt->callno]);
01875
01876 iax2_destroy_helper(pvt);
01877
01878 sched_delay_remove(&pvt->addr, pvt->callno_entry);
01879 pvt->callno_entry = NULL;
01880
01881
01882 ast_set_flag64(pvt, IAX_ALREADYGONE);
01883
01884 AST_LIST_TRAVERSE(&frame_queue[pvt->callno], cur, list) {
01885
01886 cur->retries = -1;
01887 }
01888
01889 ast_mutex_unlock(&iaxsl[pvt->callno]);
01890
01891 while ((s = AST_LIST_REMOVE_HEAD(&pvt->signaling_queue, next))) {
01892 free_signaling_queue_entry(s);
01893 }
01894
01895 if (pvt->reg) {
01896 pvt->reg->callno = 0;
01897 }
01898
01899 if (!pvt->owner) {
01900 jb_frame frame;
01901 if (pvt->vars) {
01902 ast_variables_destroy(pvt->vars);
01903 pvt->vars = NULL;
01904 }
01905
01906 while (jb_getall(pvt->jb, &frame) == JB_OK) {
01907 iax2_frame_free(frame.data);
01908 }
01909
01910 jb_destroy(pvt->jb);
01911 ast_string_field_free_memory(pvt);
01912 }
01913 }
01914
01915 static struct chan_iax2_pvt *new_iax(struct sockaddr_in *sin, const char *host)
01916 {
01917 struct chan_iax2_pvt *tmp;
01918 jb_conf jbconf;
01919
01920 if (!(tmp = ao2_alloc(sizeof(*tmp), pvt_destructor))) {
01921 return NULL;
01922 }
01923
01924 if (ast_string_field_init(tmp, 32)) {
01925 ao2_ref(tmp, -1);
01926 tmp = NULL;
01927 return NULL;
01928 }
01929
01930 tmp->prefs = prefs;
01931 tmp->pingid = -1;
01932 tmp->lagid = -1;
01933 tmp->autoid = -1;
01934 tmp->authid = -1;
01935 tmp->initid = -1;
01936 tmp->keyrotateid = -1;
01937
01938 ast_string_field_set(tmp,exten, "s");
01939 ast_string_field_set(tmp,host, host);
01940
01941 tmp->jb = jb_new();
01942 tmp->jbid = -1;
01943 jbconf.max_jitterbuf = maxjitterbuffer;
01944 jbconf.resync_threshold = resyncthreshold;
01945 jbconf.max_contig_interp = maxjitterinterps;
01946 jbconf.target_extra = jittertargetextra;
01947 jb_setconf(tmp->jb,&jbconf);
01948
01949 AST_LIST_HEAD_INIT_NOLOCK(&tmp->dpentries);
01950
01951 tmp->hold_signaling = 1;
01952 AST_LIST_HEAD_INIT_NOLOCK(&tmp->signaling_queue);
01953
01954 return tmp;
01955 }
01956
01957 static struct iax_frame *iaxfrdup2(struct iax_frame *fr)
01958 {
01959 struct iax_frame *new = iax_frame_new(DIRECTION_INGRESS, fr->af.datalen, fr->cacheable);
01960 if (new) {
01961 size_t afdatalen = new->afdatalen;
01962 memcpy(new, fr, sizeof(*new));
01963 iax_frame_wrap(new, &fr->af);
01964 new->afdatalen = afdatalen;
01965 new->data = NULL;
01966 new->datalen = 0;
01967 new->direction = DIRECTION_INGRESS;
01968 new->retrans = -1;
01969 }
01970 return new;
01971 }
01972
01973
01974 enum {
01975
01976 NEW_PREVENT = 0,
01977
01978 NEW_ALLOW = 1,
01979
01980 NEW_FORCE = 2,
01981
01982
01983 NEW_ALLOW_CALLTOKEN_VALIDATED = 3,
01984 };
01985
01986 static int match(struct sockaddr_in *sin, unsigned short callno, unsigned short dcallno, const struct chan_iax2_pvt *cur, int check_dcallno)
01987 {
01988 if ((cur->addr.sin_addr.s_addr == sin->sin_addr.s_addr) &&
01989 (cur->addr.sin_port == sin->sin_port)) {
01990
01991 if ( (cur->peercallno == 0 || cur->peercallno == callno) &&
01992 (check_dcallno ? dcallno == cur->callno : 1) ) {
01993
01994 return 1;
01995 }
01996 }
01997 if ((cur->transfer.sin_addr.s_addr == sin->sin_addr.s_addr) &&
01998 (cur->transfer.sin_port == sin->sin_port) && (cur->transferring)) {
01999
02000 if ((dcallno == cur->callno) || (cur->transferring == TRANSFER_MEDIAPASS && cur->transfercallno == callno))
02001 return 1;
02002 }
02003 return 0;
02004 }
02005
02006 #ifdef IAX_OLD_FIND
02007
02008 static int maxtrunkcall = TRUNK_CALL_START;
02009 static int maxnontrunkcall = 1;
02010
02011 #define update_max_trunk() __update_max_trunk()
02012 #define update_max_nontrunk() __update_max_nontrunk()
02013
02014 static void __update_max_trunk(void)
02015 {
02016 int max = TRUNK_CALL_START;
02017 int x;
02018
02019
02020 for (x = TRUNK_CALL_START; x < ARRAY_LEN(iaxs) - 1; x++) {
02021 if (iaxs[x]) {
02022 max = x + 1;
02023 }
02024 }
02025
02026 maxtrunkcall = max;
02027 if (iaxdebug)
02028 ast_debug(1, "New max trunk callno is %d\n", max);
02029 }
02030
02031 static void __update_max_nontrunk(void)
02032 {
02033 int max = 1;
02034 int x;
02035
02036 for (x=1;x<TRUNK_CALL_START - 1; x++) {
02037 if (iaxs[x])
02038 max = x + 1;
02039 }
02040 maxnontrunkcall = max;
02041 if (iaxdebug)
02042 ast_debug(1, "New max nontrunk callno is %d\n", max);
02043 }
02044
02045 #else
02046
02047 #define update_max_trunk() do { } while (0)
02048 #define update_max_nontrunk() do { } while (0)
02049
02050 #endif
02051
02052 static int make_trunk(unsigned short callno, int locked)
02053 {
02054 int x;
02055 int res= 0;
02056 struct callno_entry *callno_entry;
02057 if (iaxs[callno]->oseqno) {
02058 ast_log(LOG_WARNING, "Can't make trunk once a call has started!\n");
02059 return -1;
02060 }
02061 if (callno & TRUNK_CALL_START) {
02062 ast_log(LOG_WARNING, "Call %d is already a trunk\n", callno);
02063 return -1;
02064 }
02065
02066 if (!(callno_entry = get_unused_callno(1, iaxs[callno]->callno_entry->validated))) {
02067 ast_log(LOG_WARNING, "Unable to trunk call: Insufficient space\n");
02068 return -1;
02069 }
02070
02071 x = callno_entry->callno;
02072 ast_mutex_lock(&iaxsl[x]);
02073
02074
02075
02076
02077
02078 ast_sched_thread_del(sched, iaxs[callno]->pingid);
02079 ast_sched_thread_del(sched, iaxs[callno]->lagid);
02080 iaxs[callno]->lagid = iaxs[callno]->pingid = -1;
02081 iaxs[x] = iaxs[callno];
02082 iaxs[x]->callno = x;
02083
02084
02085
02086 if (iaxs[x]->callno_entry) {
02087 iax2_sched_add(sched, MIN_REUSE_TIME * 1000, replace_callno, iaxs[x]->callno_entry);
02088 }
02089 iaxs[x]->callno_entry = callno_entry;
02090
02091 iaxs[callno] = NULL;
02092
02093 iaxs[x]->pingid = iax2_sched_add(sched,
02094 ping_time * 1000, send_ping, (void *)(long)x);
02095 iaxs[x]->lagid = iax2_sched_add(sched,
02096 lagrq_time * 1000, send_lagrq, (void *)(long)x);
02097
02098 if (locked)
02099 ast_mutex_unlock(&iaxsl[callno]);
02100 res = x;
02101 if (!locked)
02102 ast_mutex_unlock(&iaxsl[x]);
02103
02104 ast_debug(1, "Made call %d into trunk call %d\n", callno, x);
02105
02106 update_max_trunk();
02107 update_max_nontrunk();
02108 return res;
02109 }
02110
02111 static void store_by_transfercallno(struct chan_iax2_pvt *pvt)
02112 {
02113 if (!pvt->transfercallno) {
02114 ast_log(LOG_ERROR, "This should not be called without a transfer call number.\n");
02115 return;
02116 }
02117
02118 ao2_link(iax_transfercallno_pvts, pvt);
02119 }
02120
02121 static void remove_by_transfercallno(struct chan_iax2_pvt *pvt)
02122 {
02123 if (!pvt->transfercallno) {
02124 ast_log(LOG_ERROR, "This should not be called without a transfer call number.\n");
02125 return;
02126 }
02127
02128 ao2_unlink(iax_transfercallno_pvts, pvt);
02129 }
02130 static void store_by_peercallno(struct chan_iax2_pvt *pvt)
02131 {
02132 if (!pvt->peercallno) {
02133 ast_log(LOG_ERROR, "This should not be called without a peer call number.\n");
02134 return;
02135 }
02136
02137 ao2_link(iax_peercallno_pvts, pvt);
02138 }
02139
02140 static void remove_by_peercallno(struct chan_iax2_pvt *pvt)
02141 {
02142 if (!pvt->peercallno) {
02143 ast_log(LOG_ERROR, "This should not be called without a peer call number.\n");
02144 return;
02145 }
02146
02147 ao2_unlink(iax_peercallno_pvts, pvt);
02148 }
02149
02150 static int addr_range_delme_cb(void *obj, void *arg, int flags)
02151 {
02152 struct addr_range *lim = obj;
02153 lim->delme = 1;
02154 return 0;
02155 }
02156
02157 static int addr_range_hash_cb(const void *obj, const int flags)
02158 {
02159 const struct addr_range *lim = obj;
02160 struct sockaddr_in sin;
02161 ast_sockaddr_to_sin(&lim->ha.addr, &sin);
02162 return abs((int) sin.sin_addr.s_addr);
02163 }
02164
02165 static int addr_range_cmp_cb(void *obj, void *arg, int flags)
02166 {
02167 struct addr_range *lim1 = obj, *lim2 = arg;
02168 return (!(ast_sockaddr_cmp_addr(&lim1->ha.addr, &lim2->ha.addr)) &&
02169 !(ast_sockaddr_cmp_addr(&lim1->ha.netmask, &lim2->ha.netmask))) ?
02170 CMP_MATCH | CMP_STOP : 0;
02171 }
02172
02173 static int peercnt_hash_cb(const void *obj, const int flags)
02174 {
02175 const struct peercnt *peercnt = obj;
02176 return abs((int) peercnt->addr);
02177 }
02178
02179 static int peercnt_cmp_cb(void *obj, void *arg, int flags)
02180 {
02181 struct peercnt *peercnt1 = obj, *peercnt2 = arg;
02182 return (peercnt1->addr == peercnt2->addr) ? CMP_MATCH | CMP_STOP : 0;
02183 }
02184
02185 static int addr_range_match_address_cb(void *obj, void *arg, int flags)
02186 {
02187 struct addr_range *addr_range = obj;
02188 struct sockaddr_in *sin = arg;
02189 struct sockaddr_in ha_netmask_sin;
02190 struct sockaddr_in ha_addr_sin;
02191
02192 ast_sockaddr_to_sin(&addr_range->ha.netmask, &ha_netmask_sin);
02193 ast_sockaddr_to_sin(&addr_range->ha.addr, &ha_addr_sin);
02194
02195 if ((sin->sin_addr.s_addr & ha_netmask_sin.sin_addr.s_addr) == ha_addr_sin.sin_addr.s_addr) {
02196 return CMP_MATCH | CMP_STOP;
02197 }
02198 return 0;
02199 }
02200
02201
02202
02203
02204
02205
02206 static int calltoken_required(struct sockaddr_in *sin, const char *name, int subclass)
02207 {
02208 struct addr_range *addr_range;
02209 struct iax2_peer *peer = NULL;
02210 struct iax2_user *user = NULL;
02211
02212 const char *find = S_OR(name, "guest");
02213 int res = 1;
02214 int optional = 0;
02215 enum calltoken_peer_enum calltoken_required = CALLTOKEN_DEFAULT;
02216
02217
02218
02219
02220
02221
02222
02223 if ((addr_range = ao2_callback(calltoken_ignores, 0, addr_range_match_address_cb, sin))) {
02224 ao2_ref(addr_range, -1);
02225 optional = 1;
02226 }
02227
02228
02229 if ((subclass == IAX_COMMAND_NEW) && (user = find_user(find))) {
02230 calltoken_required = user->calltoken_required;
02231 } else if ((subclass == IAX_COMMAND_NEW) && (user = realtime_user(find, sin))) {
02232 calltoken_required = user->calltoken_required;
02233 } else if ((subclass != IAX_COMMAND_NEW) && (peer = find_peer(find, 0))) {
02234 calltoken_required = peer->calltoken_required;
02235 } else if ((subclass != IAX_COMMAND_NEW) && (peer = realtime_peer(find, sin))) {
02236 calltoken_required = peer->calltoken_required;
02237 }
02238
02239 if (peer) {
02240 peer_unref(peer);
02241 }
02242 if (user) {
02243 user_unref(user);
02244 }
02245
02246 ast_debug(1, "Determining if address %s with username %s requires calltoken validation. Optional = %d calltoken_required = %d \n", ast_inet_ntoa(sin->sin_addr), name, optional, calltoken_required);
02247 if (((calltoken_required == CALLTOKEN_NO) || (calltoken_required == CALLTOKEN_AUTO)) ||
02248 (optional && (calltoken_required == CALLTOKEN_DEFAULT))) {
02249 res = 0;
02250 }
02251
02252 return res;
02253 }
02254
02255
02256
02257
02258
02259
02260
02261
02262
02263
02264
02265 static void set_peercnt_limit(struct peercnt *peercnt)
02266 {
02267 uint16_t limit = global_maxcallno;
02268 struct addr_range *addr_range;
02269 struct sockaddr_in sin = {
02270 .sin_addr.s_addr = peercnt->addr,
02271 };
02272
02273
02274 if (peercnt->reg && peercnt->limit) {
02275 return;
02276 }
02277
02278 if ((addr_range = ao2_callback(callno_limits, 0, addr_range_match_address_cb, &sin))) {
02279 limit = addr_range->limit;
02280 ast_debug(1, "custom addr_range %d found for %s\n", limit, ast_inet_ntoa(sin.sin_addr));
02281 ao2_ref(addr_range, -1);
02282 }
02283
02284 peercnt->limit = limit;
02285 }
02286
02287
02288
02289
02290
02291 static int set_peercnt_limit_all_cb(void *obj, void *arg, int flags)
02292 {
02293 struct peercnt *peercnt = obj;
02294
02295 set_peercnt_limit(peercnt);
02296 ast_debug(1, "Reset limits for peercnts table\n");
02297
02298 return 0;
02299 }
02300
02301
02302
02303
02304
02305 static int prune_addr_range_cb(void *obj, void *arg, int flags)
02306 {
02307 struct addr_range *addr_range = obj;
02308
02309 return addr_range->delme ? CMP_MATCH : 0;
02310 }
02311
02312
02313
02314
02315
02316 static void peercnt_modify(unsigned char reg, uint16_t limit, struct ast_sockaddr *sockaddr)
02317 {
02318
02319 struct peercnt *peercnt;
02320 struct peercnt tmp = {
02321 .addr = 0,
02322 };
02323 struct sockaddr_in sin;
02324
02325 ast_sockaddr_to_sin(sockaddr, &sin);
02326
02327 tmp.addr = sin.sin_addr.s_addr;
02328
02329 if ((peercnt = ao2_find(peercnts, &tmp, OBJ_POINTER))) {
02330 peercnt->reg = reg;
02331 if (limit) {
02332 peercnt->limit = limit;
02333 } else {
02334 set_peercnt_limit(peercnt);
02335 }
02336 ast_debug(1, "peercnt entry %s modified limit:%d registered:%d", ast_inet_ntoa(sin.sin_addr), peercnt->limit, peercnt->reg);
02337 ao2_ref(peercnt, -1);
02338 }
02339 }
02340
02341
02342
02343
02344
02345
02346
02347
02348
02349 static int peercnt_add(struct sockaddr_in *sin)
02350 {
02351 struct peercnt *peercnt;
02352 unsigned long addr = sin->sin_addr.s_addr;
02353 int res = 0;
02354 struct peercnt tmp = {
02355 .addr = addr,
02356 };
02357
02358
02359
02360
02361
02362
02363
02364 ao2_lock(peercnts);
02365 if ((peercnt = ao2_find(peercnts, &tmp, OBJ_POINTER))) {
02366 ao2_lock(peercnt);
02367 } else if ((peercnt = ao2_alloc(sizeof(*peercnt), NULL))) {
02368 ao2_lock(peercnt);
02369
02370 peercnt->addr = addr;
02371 set_peercnt_limit(peercnt);
02372
02373
02374 ao2_link(peercnts, peercnt);
02375 } else {
02376 ao2_unlock(peercnts);
02377 return -1;
02378 }
02379
02380
02381 if (peercnt->limit > peercnt->cur) {
02382 peercnt->cur++;
02383 ast_debug(1, "ip callno count incremented to %d for %s\n", peercnt->cur, ast_inet_ntoa(sin->sin_addr));
02384 } else {
02385 ast_log(LOG_ERROR, "maxcallnumber limit of %d for %s has been reached!\n", peercnt->limit, ast_inet_ntoa(sin->sin_addr));
02386 res = -1;
02387 }
02388
02389
02390 ao2_unlock(peercnt);
02391 ao2_unlock(peercnts);
02392 ao2_ref(peercnt, -1);
02393
02394 return res;
02395 }
02396
02397
02398
02399
02400
02401 static void peercnt_remove(struct peercnt *peercnt)
02402 {
02403 struct sockaddr_in sin = {
02404 .sin_addr.s_addr = peercnt->addr,
02405 };
02406
02407
02408
02409
02410
02411
02412
02413 ao2_lock(peercnts);
02414 peercnt->cur--;
02415 ast_debug(1, "ip callno count decremented to %d for %s\n", peercnt->cur, ast_inet_ntoa(sin.sin_addr));
02416
02417 if (peercnt->cur == 0) {
02418 ao2_unlink(peercnts, peercnt);
02419 }
02420 ao2_unlock(peercnts);
02421 }
02422
02423
02424
02425
02426
02427 static int peercnt_remove_cb(const void *obj)
02428 {
02429 struct peercnt *peercnt = (struct peercnt *) obj;
02430
02431 peercnt_remove(peercnt);
02432 ao2_ref(peercnt, -1);
02433
02434 return 0;
02435 }
02436
02437
02438
02439
02440
02441 static int peercnt_remove_by_addr(struct sockaddr_in *sin)
02442 {
02443 struct peercnt *peercnt;
02444 struct peercnt tmp = {
02445 .addr = sin->sin_addr.s_addr,
02446 };
02447
02448 if ((peercnt = ao2_find(peercnts, &tmp, OBJ_POINTER))) {
02449 peercnt_remove(peercnt);
02450 ao2_ref(peercnt, -1);
02451 }
02452 return 0;
02453 }
02454
02455
02456
02457
02458
02459 static void build_callno_limits(struct ast_variable *v)
02460 {
02461 struct addr_range *addr_range = NULL;
02462 struct addr_range tmp;
02463 struct ast_ha *ha;
02464 int limit;
02465 int error;
02466 int found;
02467
02468 for (; v; v = v->next) {
02469 limit = -1;
02470 error = 0;
02471 found = 0;
02472 ha = ast_append_ha("permit", v->name, NULL, &error);
02473
02474
02475 if (error) {
02476 ast_log(LOG_ERROR, "Call number limit for %s could not be added, Invalid address range\n.", v->name);
02477 continue;
02478 } else if ((sscanf(v->value, "%d", &limit) != 1) || (limit < 0)) {
02479 ast_log(LOG_ERROR, "Call number limit for %s could not be added. Invalid limit %s\n.", v->name, v->value);
02480 ast_free_ha(ha);
02481 continue;
02482 }
02483
02484 ast_copy_ha(ha, &tmp.ha);
02485
02486 if ((addr_range = ao2_find(callno_limits, &tmp, OBJ_POINTER))) {
02487 ao2_lock(addr_range);
02488 found = 1;
02489 } else if (!(addr_range = ao2_alloc(sizeof(*addr_range), NULL))) {
02490 ast_free_ha(ha);
02491 return;
02492 }
02493
02494
02495 ast_copy_ha(ha, &addr_range->ha);
02496 ast_free_ha(ha);
02497 addr_range->limit = limit;
02498 addr_range->delme = 0;
02499
02500
02501 if (found) {
02502 ao2_unlock(addr_range);
02503 } else {
02504 ao2_link(callno_limits, addr_range);
02505 }
02506 ao2_ref(addr_range, -1);
02507 }
02508 }
02509
02510
02511
02512
02513
02514 static int add_calltoken_ignore(const char *addr)
02515 {
02516 struct addr_range tmp;
02517 struct addr_range *addr_range = NULL;
02518 struct ast_ha *ha = NULL;
02519 int error = 0;
02520
02521 if (ast_strlen_zero(addr)) {
02522 ast_log(LOG_WARNING, "invalid calltokenoptional %s\n", addr);
02523 return -1;
02524 }
02525
02526 ha = ast_append_ha("permit", addr, NULL, &error);
02527
02528
02529 if (error) {
02530 ast_log(LOG_WARNING, "Error %d creating calltokenoptional entry %s\n", error, addr);
02531 return -1;
02532 }
02533
02534 ast_copy_ha(ha, &tmp.ha);
02535
02536 if ((addr_range = ao2_find(calltoken_ignores, &tmp, OBJ_POINTER))) {
02537 ao2_lock(addr_range);
02538 addr_range->delme = 0;
02539 ao2_unlock(addr_range);
02540 } else if ((addr_range = ao2_alloc(sizeof(*addr_range), NULL))) {
02541
02542 ast_copy_ha(ha, &addr_range->ha);
02543 ao2_link(calltoken_ignores, addr_range);
02544 } else {
02545 ast_free_ha(ha);
02546 return -1;
02547 }
02548
02549 ast_free_ha(ha);
02550 ao2_ref(addr_range, -1);
02551
02552 return 0;
02553 }
02554
02555 static char *handle_cli_iax2_show_callno_limits(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
02556 {
02557 struct ao2_iterator i;
02558 struct peercnt *peercnt;
02559 struct sockaddr_in sin;
02560 int found = 0;
02561
02562 switch (cmd) {
02563 case CLI_INIT:
02564 e->command = "iax2 show callnumber usage";
02565 e->usage =
02566 "Usage: iax2 show callnumber usage [IP address]\n"
02567 " Shows current IP addresses which are consuming iax2 call numbers\n";
02568 return NULL;
02569 case CLI_GENERATE:
02570 return NULL;
02571 case CLI_HANDLER:
02572 if (a->argc < 4 || a->argc > 5)
02573 return CLI_SHOWUSAGE;
02574
02575 if (a->argc == 4) {
02576 ast_cli(a->fd, "%-15s %-12s %-12s\n", "Address", "Callno Usage", "Callno Limit");
02577 }
02578
02579 i = ao2_iterator_init(peercnts, 0);
02580 while ((peercnt = ao2_iterator_next(&i))) {
02581 sin.sin_addr.s_addr = peercnt->addr;
02582 if (a->argc == 5) {
02583 if (!strcasecmp(a->argv[4], ast_inet_ntoa(sin.sin_addr))) {
02584 ast_cli(a->fd, "%-15s %-12s %-12s\n", "Address", "Callno Usage", "Callno Limit");
02585 ast_cli(a->fd, "%-15s %-12d %-12d\n", ast_inet_ntoa(sin.sin_addr), peercnt->cur, peercnt->limit);
02586 ao2_ref(peercnt, -1);
02587 found = 1;
02588 break;
02589 }
02590 } else {
02591 ast_cli(a->fd, "%-15s %-12d %-12d\n", ast_inet_ntoa(sin.sin_addr), peercnt->cur, peercnt->limit);
02592 }
02593 ao2_ref(peercnt, -1);
02594 }
02595 ao2_iterator_destroy(&i);
02596
02597 if (a->argc == 4) {
02598 ast_cli(a->fd, "\nNon-CallToken Validation Callno Limit: %d\n"
02599 "Non-CallToken Validated Callno Used: %d\n",
02600 global_maxcallno_nonval,
02601 total_nonval_callno_used);
02602
02603 ast_cli(a->fd, "Total Available Callno: %d\n"
02604 "Regular Callno Available: %d\n"
02605 "Trunk Callno Available: %d\n",
02606 ao2_container_count(callno_pool) + ao2_container_count(callno_pool_trunk),
02607 ao2_container_count(callno_pool),
02608 ao2_container_count(callno_pool_trunk));
02609 } else if (a->argc == 5 && !found) {
02610 ast_cli(a->fd, "No call number table entries for %s found\n", a->argv[4] );
02611 }
02612
02613
02614 return CLI_SUCCESS;
02615 default:
02616 return NULL;
02617 }
02618 }
02619
02620 static struct callno_entry *get_unused_callno(int trunk, int validated)
02621 {
02622 struct callno_entry *callno_entry = NULL;
02623 if ((!ao2_container_count(callno_pool) && !trunk) || (!ao2_container_count(callno_pool_trunk) && trunk)) {
02624 ast_log(LOG_WARNING, "Out of CallNumbers\n");
02625
02626 return NULL;
02627 }
02628
02629
02630
02631 ao2_lock(callno_pool);
02632
02633
02634
02635
02636 if (!validated && (total_nonval_callno_used >= global_maxcallno_nonval)) {
02637 ast_log(LOG_WARNING, "NON-CallToken callnumber limit is reached. Current:%d Max:%d\n", total_nonval_callno_used, global_maxcallno_nonval);
02638 ao2_unlock(callno_pool);
02639 return NULL;
02640 }
02641
02642
02643
02644 callno_entry = ao2_find((trunk ? callno_pool_trunk : callno_pool), NULL, OBJ_POINTER | OBJ_UNLINK | OBJ_CONTINUE);
02645
02646 if (callno_entry) {
02647 callno_entry->validated = validated;
02648 if (!validated) {
02649 total_nonval_callno_used++;
02650 }
02651 }
02652
02653 ao2_unlock(callno_pool);
02654 return callno_entry;
02655 }
02656
02657 static int replace_callno(const void *obj)
02658 {
02659 struct callno_entry *callno_entry = (struct callno_entry *) obj;
02660
02661
02662
02663 ao2_lock(callno_pool);
02664
02665 if (!callno_entry->validated && (total_nonval_callno_used != 0)) {
02666 total_nonval_callno_used--;
02667 } else if (!callno_entry->validated && (total_nonval_callno_used == 0)) {
02668 ast_log(LOG_ERROR, "Attempted to decrement total non calltoken validated callnumbers below zero... Callno is:%d \n", callno_entry->callno);
02669 }
02670
02671 if (callno_entry->callno < TRUNK_CALL_START) {
02672 ao2_link(callno_pool, callno_entry);
02673 } else {
02674 ao2_link(callno_pool_trunk, callno_entry);
02675 }
02676 ao2_ref(callno_entry, -1);
02677
02678 ao2_unlock(callno_pool);
02679 return 0;
02680 }
02681
02682 static int callno_hash(const void *obj, const int flags)
02683 {
02684 return abs(ast_random());
02685 }
02686
02687 static int create_callno_pools(void)
02688 {
02689 uint16_t i;
02690
02691 if (!(callno_pool = ao2_container_alloc(CALLNO_POOL_BUCKETS, callno_hash, NULL))) {
02692 return -1;
02693 }
02694
02695 if (!(callno_pool_trunk = ao2_container_alloc(CALLNO_POOL_BUCKETS, callno_hash, NULL))) {
02696 return -1;
02697 }
02698
02699
02700 for (i = 2; i <= IAX_MAX_CALLS; i++) {
02701 struct callno_entry *callno_entry;
02702
02703 if (!(callno_entry = ao2_alloc(sizeof(*callno_entry), NULL))) {
02704 return -1;
02705 }
02706
02707 callno_entry->callno = i;
02708
02709 if (i < TRUNK_CALL_START) {
02710 ao2_link(callno_pool, callno_entry);
02711 } else {
02712 ao2_link(callno_pool_trunk, callno_entry);
02713 }
02714
02715 ao2_ref(callno_entry, -1);
02716 }
02717
02718 return 0;
02719 }
02720
02721
02722
02723
02724
02725
02726
02727
02728
02729 static void sched_delay_remove(struct sockaddr_in *sin, struct callno_entry *callno_entry)
02730 {
02731 int i;
02732 struct peercnt *peercnt;
02733 struct peercnt tmp = {
02734 .addr = sin->sin_addr.s_addr,
02735 };
02736
02737 if ((peercnt = ao2_find(peercnts, &tmp, OBJ_POINTER))) {
02738
02739 ast_debug(1, "schedule decrement of callno used for %s in %d seconds\n", ast_inet_ntoa(sin->sin_addr), MIN_REUSE_TIME);
02740 i = iax2_sched_add(sched, MIN_REUSE_TIME * 1000, peercnt_remove_cb, peercnt);
02741 if (i == -1) {
02742 ao2_ref(peercnt, -1);
02743 }
02744 }
02745
02746 iax2_sched_add(sched, MIN_REUSE_TIME * 1000, replace_callno, callno_entry);
02747 }
02748
02749
02750
02751
02752
02753
02754
02755
02756 static inline int attribute_pure iax2_allow_new(int frametype, int subclass, int inbound)
02757 {
02758 if (frametype != AST_FRAME_IAX) {
02759 return 0;
02760 }
02761 switch (subclass) {
02762 case IAX_COMMAND_NEW:
02763 case IAX_COMMAND_REGREQ:
02764 case IAX_COMMAND_FWDOWNL:
02765 case IAX_COMMAND_REGREL:
02766 return 1;
02767 case IAX_COMMAND_POKE:
02768 if (!inbound) {
02769 return 1;
02770 }
02771 break;
02772 }
02773 return 0;
02774 }
02775
02776
02777
02778
02779 static int __find_callno(unsigned short callno, unsigned short dcallno, struct sockaddr_in *sin, int new, int sockfd, int return_locked, int check_dcallno)
02780 {
02781 int res = 0;
02782 int x;
02783
02784
02785 int validated = (new > NEW_ALLOW) ? 1 : 0;
02786 char host[80];
02787
02788 if (new <= NEW_ALLOW) {
02789 if (callno) {
02790 struct chan_iax2_pvt *pvt;
02791 struct chan_iax2_pvt tmp_pvt = {
02792 .callno = dcallno,
02793 .peercallno = callno,
02794 .transfercallno = callno,
02795
02796 .frames_received = check_dcallno,
02797 };
02798
02799 memcpy(&tmp_pvt.addr, sin, sizeof(tmp_pvt.addr));
02800
02801 if ((pvt = ao2_find(iax_peercallno_pvts, &tmp_pvt, OBJ_POINTER))) {
02802 if (return_locked) {
02803 ast_mutex_lock(&iaxsl[pvt->callno]);
02804 }
02805 res = pvt->callno;
02806 ao2_ref(pvt, -1);
02807 pvt = NULL;
02808 return res;
02809 }
02810
02811 memset(&tmp_pvt.addr, 0, sizeof(tmp_pvt.addr));
02812 memcpy(&tmp_pvt.transfer, sin, sizeof(tmp_pvt.transfer));
02813 if ((pvt = ao2_find(iax_transfercallno_pvts, &tmp_pvt, OBJ_POINTER))) {
02814 if (return_locked) {
02815 ast_mutex_lock(&iaxsl[pvt->callno]);
02816 }
02817 res = pvt->callno;
02818 ao2_ref(pvt, -1);
02819 pvt = NULL;
02820 return res;
02821 }
02822 }
02823
02824
02825 if (dcallno) {
02826 ast_mutex_lock(&iaxsl[dcallno]);
02827 }
02828 if (callno && dcallno && iaxs[dcallno] && !iaxs[dcallno]->peercallno && match(sin, callno, dcallno, iaxs[dcallno], check_dcallno)) {
02829 iaxs[dcallno]->peercallno = callno;
02830 res = dcallno;
02831 store_by_peercallno(iaxs[dcallno]);
02832 if (!res || !return_locked) {
02833 ast_mutex_unlock(&iaxsl[dcallno]);
02834 }
02835 return res;
02836 }
02837 if (dcallno) {
02838 ast_mutex_unlock(&iaxsl[dcallno]);
02839 }
02840 #ifdef IAX_OLD_FIND
02841
02842
02843
02844
02845
02846
02847
02848
02849
02850
02851
02852 for (x = 1; !res && x < maxnontrunkcall; x++) {
02853 ast_mutex_lock(&iaxsl[x]);
02854 if (iaxs[x]) {
02855
02856 if (match(sin, callno, dcallno, iaxs[x], check_dcallno)) {
02857 res = x;
02858 }
02859 }
02860 if (!res || !return_locked)
02861 ast_mutex_unlock(&iaxsl[x]);
02862 }
02863 for (x = TRUNK_CALL_START; !res && x < maxtrunkcall; x++) {
02864 ast_mutex_lock(&iaxsl[x]);
02865 if (iaxs[x]) {
02866
02867 if (match(sin, callno, dcallno, iaxs[x], check_dcallno)) {
02868 res = x;
02869 }
02870 }
02871 if (!res || !return_locked)
02872 ast_mutex_unlock(&iaxsl[x]);
02873 }
02874 #endif
02875 }
02876 if (!res && (new >= NEW_ALLOW)) {
02877 struct callno_entry *callno_entry;
02878
02879
02880
02881
02882
02883
02884 if (!iax2_getpeername(*sin, host, sizeof(host)))
02885 snprintf(host, sizeof(host), "%s:%d", ast_inet_ntoa(sin->sin_addr), ntohs(sin->sin_port));
02886
02887 if (peercnt_add(sin)) {
02888
02889
02890 return 0;
02891 }
02892
02893 if (!(callno_entry = get_unused_callno(0, validated))) {
02894
02895
02896 peercnt_remove_by_addr(sin);
02897 ast_log(LOG_WARNING, "No more space\n");
02898 return 0;
02899 }
02900 x = callno_entry->callno;
02901 ast_mutex_lock(&iaxsl[x]);
02902
02903 iaxs[x] = new_iax(sin, host);
02904 update_max_nontrunk();
02905 if (iaxs[x]) {
02906 if (iaxdebug)
02907 ast_debug(1, "Creating new call structure %d\n", x);
02908 iaxs[x]->callno_entry = callno_entry;
02909 iaxs[x]->sockfd = sockfd;
02910 iaxs[x]->addr.sin_port = sin->sin_port;
02911 iaxs[x]->addr.sin_family = sin->sin_family;
02912 iaxs[x]->addr.sin_addr.s_addr = sin->sin_addr.s_addr;
02913 iaxs[x]->peercallno = callno;
02914 iaxs[x]->callno = x;
02915 iaxs[x]->pingtime = DEFAULT_RETRY_TIME;
02916 iaxs[x]->expiry = min_reg_expire;
02917 iaxs[x]->pingid = iax2_sched_add(sched, ping_time * 1000, send_ping, (void *)(long)x);
02918 iaxs[x]->lagid = iax2_sched_add(sched, lagrq_time * 1000, send_lagrq, (void *)(long)x);
02919 iaxs[x]->amaflags = amaflags;
02920 ast_copy_flags64(iaxs[x], &globalflags, IAX_NOTRANSFER | IAX_TRANSFERMEDIA | IAX_USEJITTERBUF | IAX_FORCEJITTERBUF | IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE | IAX_FORCE_ENCRYPT);
02921 ast_string_field_set(iaxs[x], accountcode, accountcode);
02922 ast_string_field_set(iaxs[x], mohinterpret, mohinterpret);
02923 ast_string_field_set(iaxs[x], mohsuggest, mohsuggest);
02924 ast_string_field_set(iaxs[x], parkinglot, default_parkinglot);
02925
02926 if (iaxs[x]->peercallno) {
02927 store_by_peercallno(iaxs[x]);
02928 }
02929 } else {
02930 ast_log(LOG_WARNING, "Out of resources\n");
02931 ast_mutex_unlock(&iaxsl[x]);
02932 replace_callno(callno_entry);
02933 return 0;
02934 }
02935 if (!return_locked)
02936 ast_mutex_unlock(&iaxsl[x]);
02937 res = x;
02938 }
02939 return res;
02940 }
02941
02942 static int find_callno(unsigned short callno, unsigned short dcallno, struct sockaddr_in *sin, int new, int sockfd, int full_frame) {
02943 return __find_callno(callno, dcallno, sin, new, sockfd, 0, full_frame);
02944 }
02945
02946 static int find_callno_locked(unsigned short callno, unsigned short dcallno, struct sockaddr_in *sin, int new, int sockfd, int full_frame) {
02947
02948 return __find_callno(callno, dcallno, sin, new, sockfd, 1, full_frame);
02949 }
02950
02951
02952
02953
02954
02955
02956
02957
02958
02959
02960
02961 static int iax2_queue_frame(int callno, struct ast_frame *f)
02962 {
02963 iax2_lock_owner(callno);
02964 if (iaxs[callno] && iaxs[callno]->owner) {
02965 ast_queue_frame(iaxs[callno]->owner, f);
02966 ast_channel_unlock(iaxs[callno]->owner);
02967 }
02968 return 0;
02969 }
02970
02971
02972
02973
02974
02975
02976
02977
02978
02979
02980
02981
02982
02983
02984 static int iax2_queue_hangup(int callno)
02985 {
02986 iax2_lock_owner(callno);
02987 if (iaxs[callno] && iaxs[callno]->owner) {
02988 ast_queue_hangup(iaxs[callno]->owner);
02989 ast_channel_unlock(iaxs[callno]->owner);
02990 }
02991 return 0;
02992 }
02993
02994
02995
02996
02997
02998
02999
03000
03001
03002
03003
03004
03005
03006
03007 static int iax2_queue_control_data(int callno,
03008 enum ast_control_frame_type control, const void *data, size_t datalen)
03009 {
03010 iax2_lock_owner(callno);
03011 if (iaxs[callno] && iaxs[callno]->owner) {
03012 ast_queue_control_data(iaxs[callno]->owner, control, data, datalen);
03013 ast_channel_unlock(iaxs[callno]->owner);
03014 }
03015 return 0;
03016 }
03017 static void destroy_firmware(struct iax_firmware *cur)
03018 {
03019
03020 if (cur->fwh) {
03021 munmap((void*)cur->fwh, ntohl(cur->fwh->datalen) + sizeof(*(cur->fwh)));
03022 }
03023 close(cur->fd);
03024 ast_free(cur);
03025 }
03026
03027 static int try_firmware(char *s)
03028 {
03029 struct stat stbuf;
03030 struct iax_firmware *cur = NULL;
03031 int ifd, fd, res, len, chunk;
03032 struct ast_iax2_firmware_header *fwh, fwh2;
03033 struct MD5Context md5;
03034 unsigned char sum[16], buf[1024];
03035 char *s2, *last;
03036
03037 if (!(s2 = alloca(strlen(s) + 100))) {
03038 ast_log(LOG_WARNING, "Alloca failed!\n");
03039 return -1;
03040 }
03041
03042 last = strrchr(s, '/');
03043 if (last)
03044 last++;
03045 else
03046 last = s;
03047
03048 snprintf(s2, strlen(s) + 100, "/var/tmp/%s-%ld", last, (unsigned long)ast_random());
03049
03050 if ((res = stat(s, &stbuf) < 0)) {
03051 ast_log(LOG_WARNING, "Failed to stat '%s': %s\n", s, strerror(errno));
03052 return -1;
03053 }
03054
03055
03056 if (S_ISDIR(stbuf.st_mode))
03057 return -1;
03058 ifd = open(s, O_RDONLY);
03059 if (ifd < 0) {
03060 ast_log(LOG_WARNING, "Cannot open '%s': %s\n", s, strerror(errno));
03061 return -1;
03062 }
03063 fd = open(s2, O_RDWR | O_CREAT | O_EXCL, AST_FILE_MODE);
03064 if (fd < 0) {
03065 ast_log(LOG_WARNING, "Cannot open '%s' for writing: %s\n", s2, strerror(errno));
03066 close(ifd);
03067 return -1;
03068 }
03069
03070 unlink(s2);
03071
03072
03073 len = stbuf.st_size;
03074 while(len) {
03075 chunk = len;
03076 if (chunk > sizeof(buf))
03077 chunk = sizeof(buf);
03078 res = read(ifd, buf, chunk);
03079 if (res != chunk) {
03080 ast_log(LOG_WARNING, "Only read %d of %d bytes of data :(: %s\n", res, chunk, strerror(errno));
03081 close(ifd);
03082 close(fd);
03083 return -1;
03084 }
03085 res = write(fd, buf, chunk);
03086 if (res != chunk) {
03087 ast_log(LOG_WARNING, "Only write %d of %d bytes of data :(: %s\n", res, chunk, strerror(errno));
03088 close(ifd);
03089 close(fd);
03090 return -1;
03091 }
03092 len -= chunk;
03093 }
03094 close(ifd);
03095
03096 lseek(fd, 0, SEEK_SET);
03097 if ((res = read(fd, &fwh2, sizeof(fwh2))) != sizeof(fwh2)) {
03098 ast_log(LOG_WARNING, "Unable to read firmware header in '%s'\n", s);
03099 close(fd);
03100 return -1;
03101 }
03102 if (ntohl(fwh2.magic) != IAX_FIRMWARE_MAGIC) {
03103 ast_log(LOG_WARNING, "'%s' is not a valid firmware file\n", s);
03104 close(fd);
03105 return -1;
03106 }
03107 if (ntohl(fwh2.datalen) != (stbuf.st_size - sizeof(fwh2))) {
03108 ast_log(LOG_WARNING, "Invalid data length in firmware '%s'\n", s);
03109 close(fd);
03110 return -1;
03111 }
03112 if (fwh2.devname[sizeof(fwh2.devname) - 1] || ast_strlen_zero((char *)fwh2.devname)) {
03113 ast_log(LOG_WARNING, "No or invalid device type specified for '%s'\n", s);
03114 close(fd);
03115 return -1;
03116 }
03117 fwh = (struct ast_iax2_firmware_header*)mmap(NULL, stbuf.st_size, PROT_READ, MAP_PRIVATE, fd, 0);
03118 if (fwh == MAP_FAILED) {
03119 ast_log(LOG_WARNING, "mmap failed: %s\n", strerror(errno));
03120 close(fd);
03121 return -1;
03122 }
03123 MD5Init(&md5);
03124 MD5Update(&md5, fwh->data, ntohl(fwh->datalen));
03125 MD5Final(sum, &md5);
03126 if (memcmp(sum, fwh->chksum, sizeof(sum))) {
03127 ast_log(LOG_WARNING, "Firmware file '%s' fails checksum\n", s);
03128 munmap((void*)fwh, stbuf.st_size);
03129 close(fd);
03130 return -1;
03131 }
03132
03133 AST_LIST_TRAVERSE(&firmwares, cur, list) {
03134 if (!strcmp((char *)cur->fwh->devname, (char *)fwh->devname)) {
03135
03136 if (cur->dead || (ntohs(cur->fwh->version) < ntohs(fwh->version)))
03137
03138 break;
03139
03140
03141 munmap((void*)fwh, stbuf.st_size);
03142 close(fd);
03143 return 0;
03144 }
03145 }
03146
03147 if (!cur && ((cur = ast_calloc(1, sizeof(*cur))))) {
03148 cur->fd = -1;
03149 AST_LIST_INSERT_TAIL(&firmwares, cur, list);
03150 }
03151
03152 if (cur) {
03153 if (cur->fwh)
03154 munmap((void*)cur->fwh, cur->mmaplen);
03155 if (cur->fd > -1)
03156 close(cur->fd);
03157 cur->fwh = fwh;
03158 cur->fd = fd;
03159 cur->mmaplen = stbuf.st_size;
03160 cur->dead = 0;
03161 }
03162
03163 return 0;
03164 }
03165
03166 static int iax_check_version(char *dev)
03167 {
03168 int res = 0;
03169 struct iax_firmware *cur = NULL;
03170
03171 if (ast_strlen_zero(dev))
03172 return 0;
03173
03174 AST_LIST_LOCK(&firmwares);
03175 AST_LIST_TRAVERSE(&firmwares, cur, list) {
03176 if (!strcmp(dev, (char *)cur->fwh->devname)) {
03177 res = ntohs(cur->fwh->version);
03178 break;
03179 }
03180 }
03181 AST_LIST_UNLOCK(&firmwares);
03182
03183 return res;
03184 }
03185
03186 static int iax_firmware_append(struct iax_ie_data *ied, const unsigned char *dev, unsigned int desc)
03187 {
03188 int res = -1;
03189 unsigned int bs = desc & 0xff;
03190 unsigned int start = (desc >> 8) & 0xffffff;
03191 unsigned int bytes;
03192 struct iax_firmware *cur;
03193
03194 if (ast_strlen_zero((char *)dev) || !bs)
03195 return -1;
03196
03197 start *= bs;
03198
03199 AST_LIST_LOCK(&firmwares);
03200 AST_LIST_TRAVERSE(&firmwares, cur, list) {
03201 if (strcmp((char *)dev, (char *)cur->fwh->devname))
03202 continue;
03203 iax_ie_append_int(ied, IAX_IE_FWBLOCKDESC, desc);
03204 if (start < ntohl(cur->fwh->datalen)) {
03205 bytes = ntohl(cur->fwh->datalen) - start;
03206 if (bytes > bs)
03207 bytes = bs;
03208 iax_ie_append_raw(ied, IAX_IE_FWBLOCKDATA, cur->fwh->data + start, bytes);
03209 } else {
03210 bytes = 0;
03211 iax_ie_append(ied, IAX_IE_FWBLOCKDATA);
03212 }
03213 if (bytes == bs)
03214 res = 0;
03215 else
03216 res = 1;
03217 break;
03218 }
03219 AST_LIST_UNLOCK(&firmwares);
03220
03221 return res;
03222 }
03223
03224
03225 static void reload_firmware(int unload)
03226 {
03227 struct iax_firmware *cur = NULL;
03228 DIR *fwd;
03229 struct dirent *de;
03230 char dir[256], fn[256];
03231
03232 AST_LIST_LOCK(&firmwares);
03233
03234
03235 AST_LIST_TRAVERSE(&firmwares, cur, list)
03236 cur->dead = 1;
03237
03238
03239 if (!unload) {
03240 snprintf(dir, sizeof(dir), "%s/firmware/iax", ast_config_AST_DATA_DIR);
03241 fwd = opendir(dir);
03242 if (fwd) {
03243 while((de = readdir(fwd))) {
03244 if (de->d_name[0] != '.') {
03245 snprintf(fn, sizeof(fn), "%s/%s", dir, de->d_name);
03246 if (!try_firmware(fn)) {
03247 ast_verb(2, "Loaded firmware '%s'\n", de->d_name);
03248 }
03249 }
03250 }
03251 closedir(fwd);
03252 } else
03253 ast_log(LOG_WARNING, "Error opening firmware directory '%s': %s\n", dir, strerror(errno));
03254 }
03255
03256
03257 AST_LIST_TRAVERSE_SAFE_BEGIN(&firmwares, cur, list) {
03258 if (!cur->dead)
03259 continue;
03260 AST_LIST_REMOVE_CURRENT(list);
03261 destroy_firmware(cur);
03262 }
03263 AST_LIST_TRAVERSE_SAFE_END;
03264
03265 AST_LIST_UNLOCK(&firmwares);
03266 }
03267
03268
03269
03270
03271
03272
03273
03274
03275
03276 static int __do_deliver(void *data)
03277 {
03278
03279
03280 struct iax_frame *fr = data;
03281 fr->retrans = -1;
03282 ast_clear_flag(&fr->af, AST_FRFLAG_HAS_TIMING_INFO);
03283 if (iaxs[fr->callno] && !ast_test_flag64(iaxs[fr->callno], IAX_ALREADYGONE))
03284 iax2_queue_frame(fr->callno, &fr->af);
03285
03286 iax2_frame_free(fr);
03287
03288 return 0;
03289 }
03290
03291 static int handle_error(void)
03292 {
03293
03294
03295
03296 #if 0
03297 struct sockaddr_in *sin;
03298 int res;
03299 struct msghdr m;
03300 struct sock_extended_err e;
03301 m.msg_name = NULL;
03302 m.msg_namelen = 0;
03303 m.msg_iov = NULL;
03304 m.msg_control = &e;
03305 m.msg_controllen = sizeof(e);
03306 m.msg_flags = 0;
03307 res = recvmsg(netsocket, &m, MSG_ERRQUEUE);
03308 if (res < 0)
03309 ast_log(LOG_WARNING, "Error detected, but unable to read error: %s\n", strerror(errno));
03310 else {
03311 if (m.msg_controllen) {
03312 sin = (struct sockaddr_in *)SO_EE_OFFENDER(&e);
03313 if (sin)
03314 ast_log(LOG_WARNING, "Receive error from %s\n", ast_inet_ntoa(sin->sin_addr));
03315 else
03316 ast_log(LOG_WARNING, "No address detected??\n");
03317 } else {
03318 ast_log(LOG_WARNING, "Local error: %s\n", strerror(e.ee_errno));
03319 }
03320 }
03321 #endif
03322 return 0;
03323 }
03324
03325 static int transmit_trunk(struct iax_frame *f, struct sockaddr_in *sin, int sockfd)
03326 {
03327 int res;
03328 res = sendto(sockfd, f->data, f->datalen, 0,(struct sockaddr *)sin,
03329 sizeof(*sin));
03330 if (res < 0) {
03331 ast_debug(1, "Received error: %s\n", strerror(errno));
03332 handle_error();
03333 } else
03334 res = 0;
03335 return res;
03336 }
03337
03338 static int send_packet(struct iax_frame *f)
03339 {
03340 int res;
03341 int callno = f->callno;
03342
03343
03344 if (!callno || !iaxs[callno] || iaxs[callno]->error)
03345 return -1;
03346
03347
03348 if (iaxdebug)
03349 ast_debug(3, "Sending %d on %d/%d to %s:%d\n", f->ts, callno, iaxs[callno]->peercallno, ast_inet_ntoa(iaxs[callno]->addr.sin_addr), ntohs(iaxs[callno]->addr.sin_port));
03350
03351 if (f->transfer) {
03352 if (iaxdebug)
03353 iax_showframe(f, NULL, 0, &iaxs[callno]->transfer, f->datalen - sizeof(struct ast_iax2_full_hdr));
03354 res = sendto(iaxs[callno]->sockfd, f->data, f->datalen, 0,(struct sockaddr *)&iaxs[callno]->transfer, sizeof(iaxs[callno]->transfer));
03355 } else {
03356 if (iaxdebug)
03357 iax_showframe(f, NULL, 0, &iaxs[callno]->addr, f->datalen - sizeof(struct ast_iax2_full_hdr));
03358 res = sendto(iaxs[callno]->sockfd, f->data, f->datalen, 0,(struct sockaddr *)&iaxs[callno]->addr, sizeof(iaxs[callno]->addr));
03359 }
03360 if (res < 0) {
03361 if (iaxdebug)
03362 ast_debug(1, "Received error: %s\n", strerror(errno));
03363 handle_error();
03364 } else
03365 res = 0;
03366
03367 return res;
03368 }
03369
03370
03371
03372
03373
03374 static int iax2_predestroy(int callno)
03375 {
03376 struct ast_channel *c = NULL;
03377 struct chan_iax2_pvt *pvt = iaxs[callno];
03378
03379 if (!pvt)
03380 return -1;
03381
03382 if (!ast_test_flag64(pvt, IAX_ALREADYGONE)) {
03383 iax2_destroy_helper(pvt);
03384 ast_set_flag64(pvt, IAX_ALREADYGONE);
03385 }
03386
03387 if ((c = pvt->owner)) {
03388 c->tech_pvt = NULL;
03389 iax2_queue_hangup(callno);
03390 pvt->owner = NULL;
03391 ast_module_unref(ast_module_info->self);
03392 }
03393
03394 return 0;
03395 }
03396
03397 static void iax2_destroy(int callno)
03398 {
03399 struct chan_iax2_pvt *pvt = NULL;
03400 struct ast_channel *owner = NULL;
03401
03402 retry:
03403 if ((pvt = iaxs[callno])) {
03404 #if 0
03405
03406
03407
03408
03409
03410
03411
03412 iax2_destroy_helper(pvt);
03413 #endif
03414 }
03415
03416 owner = pvt ? pvt->owner : NULL;
03417
03418 if (owner) {
03419 if (ast_channel_trylock(owner)) {
03420 ast_debug(3, "Avoiding IAX destroy deadlock\n");
03421 DEADLOCK_AVOIDANCE(&iaxsl[callno]);
03422 goto retry;
03423 }
03424 }
03425
03426 if (!owner) {
03427 iaxs[callno] = NULL;
03428 }
03429
03430 if (pvt) {
03431 if (!owner) {
03432 pvt->owner = NULL;
03433 } else {
03434
03435
03436
03437 ast_queue_hangup(owner);
03438 }
03439
03440 if (pvt->peercallno) {
03441 remove_by_peercallno(pvt);
03442 }
03443
03444 if (pvt->transfercallno) {
03445 remove_by_transfercallno(pvt);
03446 }
03447
03448 if (!owner) {
03449 ao2_ref(pvt, -1);
03450 pvt = NULL;
03451 }
03452 }
03453
03454 if (owner) {
03455 ast_channel_unlock(owner);
03456 }
03457
03458 if (callno & TRUNK_CALL_START) {
03459 update_max_trunk();
03460 }
03461 }
03462
03463 static int update_packet(struct iax_frame *f)
03464 {
03465
03466 struct ast_iax2_full_hdr *fh = f->data;
03467 struct ast_frame af;
03468
03469
03470 if (f->encmethods) {
03471 decode_frame(&f->mydcx, fh, &af, &f->datalen);
03472 }
03473
03474 fh->dcallno = ntohs(IAX_FLAG_RETRANS | f->dcallno);
03475
03476 f->iseqno = iaxs[f->callno]->iseqno;
03477 fh->iseqno = f->iseqno;
03478
03479
03480 if (f->encmethods) {
03481
03482
03483 build_rand_pad(f->semirand, sizeof(f->semirand));
03484 encrypt_frame(&f->ecx, fh, f->semirand, &f->datalen);
03485 }
03486 return 0;
03487 }
03488
03489 static int attempt_transmit(const void *data);
03490 static void __attempt_transmit(const void *data)
03491 {
03492
03493
03494 struct iax_frame *f = (struct iax_frame *)data;
03495 int freeme = 0;
03496 int callno = f->callno;
03497
03498 if (callno)
03499 ast_mutex_lock(&iaxsl[callno]);
03500 if (callno && iaxs[callno]) {
03501 if ((f->retries < 0) ||
03502 (f->retries >= max_retries) ) {
03503
03504 if (f->retries >= max_retries) {
03505 if (f->transfer) {
03506
03507 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_TXREJ, 0, NULL, 0, -1);
03508 } else if (f->final) {
03509 iax2_destroy(callno);
03510 } else {
03511 if (iaxs[callno]->owner)
03512 ast_log(LOG_WARNING, "Max retries exceeded to host %s on %s (type = %d, subclass = %u, ts=%d, seqno=%d)\n", ast_inet_ntoa(iaxs[f->callno]->addr.sin_addr),iaxs[f->callno]->owner->name , f->af.frametype, f->af.subclass.integer, f->ts, f->oseqno);
03513 iaxs[callno]->error = ETIMEDOUT;
03514 if (iaxs[callno]->owner) {
03515 struct ast_frame fr = { AST_FRAME_CONTROL, { AST_CONTROL_HANGUP }, .data.uint32 = AST_CAUSE_DESTINATION_OUT_OF_ORDER };
03516
03517 iax2_queue_frame(callno, &fr);
03518
03519 if (iaxs[callno] && iaxs[callno]->owner)
03520 iaxs[callno]->owner->hangupcause = AST_CAUSE_DESTINATION_OUT_OF_ORDER;
03521 } else {
03522 if (iaxs[callno]->reg) {
03523 memset(&iaxs[callno]->reg->us, 0, sizeof(iaxs[callno]->reg->us));
03524 iaxs[callno]->reg->regstate = REG_STATE_TIMEOUT;
03525 iaxs[callno]->reg->refresh = IAX_DEFAULT_REG_EXPIRE;
03526 }
03527 iax2_destroy(callno);
03528 }
03529 }
03530
03531 }
03532 freeme = 1;
03533 } else {
03534
03535 update_packet(f);
03536
03537 send_packet(f);
03538 f->retries++;
03539
03540 f->retrytime *= 10;
03541 if (f->retrytime > MAX_RETRY_TIME)
03542 f->retrytime = MAX_RETRY_TIME;
03543
03544 if (f->transfer && (f->retrytime > 1000))
03545 f->retrytime = 1000;
03546 f->retrans = iax2_sched_add(sched, f->retrytime, attempt_transmit, f);
03547 }
03548 } else {
03549
03550 f->retries = -1;
03551 freeme = 1;
03552 }
03553
03554 if (freeme) {
03555
03556 AST_LIST_REMOVE(&frame_queue[callno], f, list);
03557 ast_mutex_unlock(&iaxsl[callno]);
03558 f->retrans = -1;
03559
03560 iax2_frame_free(f);
03561 } else if (callno) {
03562 ast_mutex_unlock(&iaxsl[callno]);
03563 }
03564 }
03565
03566 static int attempt_transmit(const void *data)
03567 {
03568 #ifdef SCHED_MULTITHREADED
03569 if (schedule_action(__attempt_transmit, data))
03570 #endif
03571 __attempt_transmit(data);
03572 return 0;
03573 }
03574
03575 static char *handle_cli_iax2_prune_realtime(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03576 {
03577 struct iax2_peer *peer = NULL;
03578 struct iax2_user *user = NULL;
03579 static const char * const choices[] = { "all", NULL };
03580 char *cmplt;
03581
03582 switch (cmd) {
03583 case CLI_INIT:
03584 e->command = "iax2 prune realtime";
03585 e->usage =
03586 "Usage: iax2 prune realtime [<peername>|all]\n"
03587 " Prunes object(s) from the cache\n";
03588 return NULL;
03589 case CLI_GENERATE:
03590 if (a->pos == 3) {
03591 cmplt = ast_cli_complete(a->word, choices, a->n);
03592 if (!cmplt)
03593 cmplt = complete_iax2_peers(a->line, a->word, a->pos, a->n - sizeof(choices), IAX_RTCACHEFRIENDS);
03594 return cmplt;
03595 }
03596 return NULL;
03597 }
03598 if (a->argc != 4)
03599 return CLI_SHOWUSAGE;
03600 if (!strcmp(a->argv[3], "all")) {
03601 prune_users();
03602 prune_peers();
03603 ast_cli(a->fd, "Cache flushed successfully.\n");
03604 return CLI_SUCCESS;
03605 }
03606 peer = find_peer(a->argv[3], 0);
03607 user = find_user(a->argv[3]);
03608 if (peer || user) {
03609 if (peer) {
03610 if (ast_test_flag64(peer, IAX_RTCACHEFRIENDS)) {
03611 ast_set_flag64(peer, IAX_RTAUTOCLEAR);
03612 expire_registry(peer_ref(peer));
03613 ast_cli(a->fd, "Peer %s was removed from the cache.\n", a->argv[3]);
03614 } else {
03615 ast_cli(a->fd, "Peer %s is not eligible for this operation.\n", a->argv[3]);
03616 }
03617 peer_unref(peer);
03618 }
03619 if (user) {
03620 if (ast_test_flag64(user, IAX_RTCACHEFRIENDS)) {
03621 ast_set_flag64(user, IAX_RTAUTOCLEAR);
03622 ast_cli(a->fd, "User %s was removed from the cache.\n", a->argv[3]);
03623 } else {
03624 ast_cli(a->fd, "User %s is not eligible for this operation.\n", a->argv[3]);
03625 }
03626 ao2_unlink(users,user);
03627 user_unref(user);
03628 }
03629 } else {
03630 ast_cli(a->fd, "%s was not found in the cache.\n", a->argv[3]);
03631 }
03632
03633 return CLI_SUCCESS;
03634 }
03635
03636 static char *handle_cli_iax2_test_losspct(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03637 {
03638 switch (cmd) {
03639 case CLI_INIT:
03640 e->command = "iax2 test losspct";
03641 e->usage =
03642 "Usage: iax2 test losspct <percentage>\n"
03643 " For testing, throws away <percentage> percent of incoming packets\n";
03644 return NULL;
03645 case CLI_GENERATE:
03646 return NULL;
03647 }
03648 if (a->argc != 4)
03649 return CLI_SHOWUSAGE;
03650
03651 test_losspct = atoi(a->argv[3]);
03652
03653 return CLI_SUCCESS;
03654 }
03655
03656 #ifdef IAXTESTS
03657 static char *handle_cli_iax2_test_late(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03658 {
03659 switch (cmd) {
03660 case CLI_INIT:
03661 e->command = "iax2 test late";
03662 e->usage =
03663 "Usage: iax2 test late <ms>\n"
03664 " For testing, count the next frame as <ms> ms late\n";
03665 return NULL;
03666 case CLI_GENERATE:
03667 return NULL;
03668 }
03669
03670 if (a->argc != 4)
03671 return CLI_SHOWUSAGE;
03672
03673 test_late = atoi(a->argv[3]);
03674
03675 return CLI_SUCCESS;
03676 }
03677
03678 static char *handle_cli_iax2_test_resync(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03679 {
03680 switch (cmd) {
03681 case CLI_INIT:
03682 e->command = "iax2 test resync";
03683 e->usage =
03684 "Usage: iax2 test resync <ms>\n"
03685 " For testing, adjust all future frames by <ms> ms\n";
03686 return NULL;
03687 case CLI_GENERATE:
03688 return NULL;
03689 }
03690
03691 if (a->argc != 4)
03692 return CLI_SHOWUSAGE;
03693
03694 test_resync = atoi(a->argv[3]);
03695
03696 return CLI_SUCCESS;
03697 }
03698
03699 static char *handle_cli_iax2_test_jitter(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03700 {
03701 switch (cmd) {
03702 case CLI_INIT:
03703 e->command = "iax2 test jitter";
03704 e->usage =
03705 "Usage: iax2 test jitter <ms> <pct>\n"
03706 " For testing, simulate maximum jitter of +/- <ms> on <pct>\n"
03707 " percentage of packets. If <pct> is not specified, adds\n"
03708 " jitter to all packets.\n";
03709 return NULL;
03710 case CLI_GENERATE:
03711 return NULL;
03712 }
03713
03714 if (a->argc < 4 || a->argc > 5)
03715 return CLI_SHOWUSAGE;
03716
03717 test_jit = atoi(a->argv[3]);
03718 if (a->argc == 5)
03719 test_jitpct = atoi(a->argv[4]);
03720
03721 return CLI_SUCCESS;
03722 }
03723 #endif
03724
03725
03726
03727 static int peer_status(struct iax2_peer *peer, char *status, int statuslen)
03728 {
03729 int res = 0;
03730 if (peer->maxms) {
03731 if (peer->lastms < 0) {
03732 ast_copy_string(status, "UNREACHABLE", statuslen);
03733 } else if (peer->lastms > peer->maxms) {
03734 snprintf(status, statuslen, "LAGGED (%d ms)", peer->lastms);
03735 res = 1;
03736 } else if (peer->lastms) {
03737 snprintf(status, statuslen, "OK (%d ms)", peer->lastms);
03738 res = 1;
03739 } else {
03740 ast_copy_string(status, "UNKNOWN", statuslen);
03741 }
03742 } else {
03743 ast_copy_string(status, "Unmonitored", statuslen);
03744 res = -1;
03745 }
03746 return res;
03747 }
03748
03749
03750 static char *handle_cli_iax2_show_peer(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03751 {
03752 char status[30];
03753 char cbuf[256];
03754 struct iax2_peer *peer;
03755 char codec_buf[512];
03756 struct ast_str *encmethods = ast_str_alloca(256);
03757 int x = 0, codec = 0, load_realtime = 0;
03758
03759 switch (cmd) {
03760 case CLI_INIT:
03761 e->command = "iax2 show peer";
03762 e->usage =
03763 "Usage: iax2 show peer <name>\n"
03764 " Display details on specific IAX peer\n";
03765 return NULL;
03766 case CLI_GENERATE:
03767 if (a->pos == 3)
03768 return complete_iax2_peers(a->line, a->word, a->pos, a->n, 0);
03769 return NULL;
03770 }
03771
03772 if (a->argc < 4)
03773 return CLI_SHOWUSAGE;
03774
03775 load_realtime = (a->argc == 5 && !strcmp(a->argv[4], "load")) ? 1 : 0;
03776
03777 peer = find_peer(a->argv[3], load_realtime);
03778 if (peer) {
03779 struct sockaddr_in peer_addr;
03780
03781 ast_sockaddr_to_sin(&peer->addr, &peer_addr);
03782
03783 encmethods_to_str(peer->encmethods, encmethods);
03784 ast_cli(a->fd, "\n\n");
03785 ast_cli(a->fd, " * Name : %s\n", peer->name);
03786 ast_cli(a->fd, " Secret : %s\n", ast_strlen_zero(peer->secret) ? "<Not set>" : "<Set>");
03787 ast_cli(a->fd, " Context : %s\n", peer->context);
03788 ast_cli(a->fd, " Parking lot : %s\n", peer->parkinglot);
03789 ast_cli(a->fd, " Mailbox : %s\n", peer->mailbox);
03790 ast_cli(a->fd, " Dynamic : %s\n", ast_test_flag64(peer, IAX_DYNAMIC) ? "Yes" : "No");
03791 ast_cli(a->fd, " Callnum limit: %d\n", peer->maxcallno);
03792 ast_cli(a->fd, " Calltoken req: %s\n", (peer->calltoken_required == CALLTOKEN_YES) ? "Yes" : ((peer->calltoken_required == CALLTOKEN_AUTO) ? "Auto" : "No"));
03793 ast_cli(a->fd, " Trunk : %s\n", ast_test_flag64(peer, IAX_TRUNK) ? "Yes" : "No");
03794 ast_cli(a->fd, " Encryption : %s\n", peer->encmethods ? ast_str_buffer(encmethods) : "No");
03795 ast_cli(a->fd, " Callerid : %s\n", ast_callerid_merge(cbuf, sizeof(cbuf), peer->cid_name, peer->cid_num, "<unspecified>"));
03796 ast_cli(a->fd, " Expire : %d\n", peer->expire);
03797 ast_cli(a->fd, " ACL : %s\n", (peer->ha ? "Yes" : "No"));
03798 ast_cli(a->fd, " Addr->IP : %s Port %d\n", peer_addr.sin_addr.s_addr ? ast_inet_ntoa(peer_addr.sin_addr) : "(Unspecified)", ntohs(peer_addr.sin_port));
03799 ast_cli(a->fd, " Defaddr->IP : %s Port %d\n", ast_inet_ntoa(peer->defaddr.sin_addr), ntohs(peer->defaddr.sin_port));
03800 ast_cli(a->fd, " Username : %s\n", peer->username);
03801 ast_cli(a->fd, " Codecs : ");
03802 ast_getformatname_multiple(codec_buf, sizeof(codec_buf) -1, peer->capability);
03803 ast_cli(a->fd, "%s\n", codec_buf);
03804
03805 ast_cli(a->fd, " Codec Order : (");
03806 for(x = 0; x < 32 ; x++) {
03807 codec = ast_codec_pref_index(&peer->prefs,x);
03808 if(!codec)
03809 break;
03810 ast_cli(a->fd, "%s", ast_getformatname(codec));
03811 if(x < 31 && ast_codec_pref_index(&peer->prefs,x+1))
03812 ast_cli(a->fd, "|");
03813 }
03814
03815 if (!x)
03816 ast_cli(a->fd, "none");
03817 ast_cli(a->fd, ")\n");
03818
03819 ast_cli(a->fd, " Status : ");
03820 peer_status(peer, status, sizeof(status));
03821 ast_cli(a->fd, "%s\n",status);
03822 ast_cli(a->fd, " Qualify : every %dms when OK, every %dms when UNREACHABLE (sample smoothing %s)\n", peer->pokefreqok, peer->pokefreqnotok, peer->smoothing ? "On" : "Off");
03823 ast_cli(a->fd, "\n");
03824 peer_unref(peer);
03825 } else {
03826 ast_cli(a->fd, "Peer %s not found.\n", a->argv[3]);
03827 ast_cli(a->fd, "\n");
03828 }
03829
03830 return CLI_SUCCESS;
03831 }
03832
03833 static char *complete_iax2_peers(const char *line, const char *word, int pos, int state, uint64_t flags)
03834 {
03835 int which = 0;
03836 struct iax2_peer *peer;
03837 char *res = NULL;
03838 int wordlen = strlen(word);
03839 struct ao2_iterator i;
03840
03841 i = ao2_iterator_init(peers, 0);
03842 while ((peer = ao2_iterator_next(&i))) {
03843 if (!strncasecmp(peer->name, word, wordlen) && ++which > state
03844 && (!flags || ast_test_flag64(peer, flags))) {
03845 res = ast_strdup(peer->name);
03846 peer_unref(peer);
03847 break;
03848 }
03849 peer_unref(peer);
03850 }
03851 ao2_iterator_destroy(&i);
03852
03853 return res;
03854 }
03855
03856 static char *handle_cli_iax2_show_stats(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03857 {
03858 struct iax_frame *cur;
03859 int cnt = 0, dead = 0, final = 0, i = 0;
03860
03861 switch (cmd) {
03862 case CLI_INIT:
03863 e->command = "iax2 show stats";
03864 e->usage =
03865 "Usage: iax2 show stats\n"
03866 " Display statistics on IAX channel driver.\n";
03867 return NULL;
03868 case CLI_GENERATE:
03869 return NULL;
03870 }
03871
03872 if (a->argc != 3)
03873 return CLI_SHOWUSAGE;
03874
03875 for (i = 0; i < ARRAY_LEN(frame_queue); i++) {
03876 ast_mutex_lock(&iaxsl[i]);
03877 AST_LIST_TRAVERSE(&frame_queue[i], cur, list) {
03878 if (cur->retries < 0)
03879 dead++;
03880 if (cur->final)
03881 final++;
03882 cnt++;
03883 }
03884 ast_mutex_unlock(&iaxsl[i]);
03885 }
03886
03887 ast_cli(a->fd, " IAX Statistics\n");
03888 ast_cli(a->fd, "---------------------\n");
03889 ast_cli(a->fd, "Outstanding frames: %d (%d ingress, %d egress)\n", iax_get_frames(), iax_get_iframes(), iax_get_oframes());
03890 ast_cli(a->fd, "%d timed and %d untimed transmits; MTU %d/%d/%d\n", trunk_timed, trunk_untimed,
03891 trunk_maxmtu, trunk_nmaxmtu, global_max_trunk_mtu);
03892 ast_cli(a->fd, "Packets in transmit queue: %d dead, %d final, %d total\n\n", dead, final, cnt);
03893
03894 trunk_timed = trunk_untimed = 0;
03895 if (trunk_maxmtu > trunk_nmaxmtu)
03896 trunk_nmaxmtu = trunk_maxmtu;
03897
03898 return CLI_SUCCESS;
03899 }
03900
03901
03902 static char *handle_cli_iax2_set_mtu(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03903 {
03904 int mtuv;
03905
03906 switch (cmd) {
03907 case CLI_INIT:
03908 e->command = "iax2 set mtu";
03909 e->usage =
03910 "Usage: iax2 set mtu <value>\n"
03911 " Set the system-wide IAX IP mtu to <value> bytes net or\n"
03912 " zero to disable. Disabling means that the operating system\n"
03913 " must handle fragmentation of UDP packets when the IAX2 trunk\n"
03914 " packet exceeds the UDP payload size. This is substantially\n"
03915 " below the IP mtu. Try 1240 on ethernets. Must be 172 or\n"
03916 " greater for G.711 samples.\n";
03917 return NULL;
03918 case CLI_GENERATE:
03919 return NULL;
03920 }
03921
03922 if (a->argc != 4)
03923 return CLI_SHOWUSAGE;
03924 if (strncasecmp(a->argv[3], "default", strlen(a->argv[3])) == 0)
03925 mtuv = MAX_TRUNK_MTU;
03926 else
03927 mtuv = atoi(a->argv[3]);
03928
03929 if (mtuv == 0) {
03930 ast_cli(a->fd, "Trunk MTU control disabled (mtu was %d)\n", global_max_trunk_mtu);
03931 global_max_trunk_mtu = 0;
03932 return CLI_SUCCESS;
03933 }
03934 if (mtuv < 172 || mtuv > 4000) {
03935 ast_cli(a->fd, "Trunk MTU must be between 172 and 4000\n");
03936 return CLI_SHOWUSAGE;
03937 }
03938 ast_cli(a->fd, "Trunk MTU changed from %d to %d\n", global_max_trunk_mtu, mtuv);
03939 global_max_trunk_mtu = mtuv;
03940 return CLI_SUCCESS;
03941 }
03942
03943 static char *handle_cli_iax2_show_cache(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
03944 {
03945 struct iax2_dpcache *dp = NULL;
03946 char tmp[1024], *pc = NULL;
03947 int s, x, y;
03948 struct timeval now = ast_tvnow();
03949
03950 switch (cmd) {
03951 case CLI_INIT:
03952 e->command = "iax2 show cache";
03953 e->usage =
03954 "Usage: iax2 show cache\n"
03955 " Display currently cached IAX Dialplan results.\n";
03956 return NULL;
03957 case CLI_GENERATE:
03958 return NULL;
03959 }
03960
03961 AST_LIST_LOCK(&dpcache);
03962
03963 ast_cli(a->fd, "%-20.20s %-12.12s %-9.9s %-8.8s %s\n", "Peer/Context", "Exten", "Exp.", "Wait.", "Flags");
03964
03965 AST_LIST_TRAVERSE(&dpcache, dp, cache_list) {
03966 s = dp->expiry.tv_sec - now.tv_sec;
03967 tmp[0] = '\0';
03968 if (dp->flags & CACHE_FLAG_EXISTS)
03969 strncat(tmp, "EXISTS|", sizeof(tmp) - strlen(tmp) - 1);
03970 if (dp->flags & CACHE_FLAG_NONEXISTENT)
03971 strncat(tmp, "NONEXISTENT|", sizeof(tmp) - strlen(tmp) - 1);
03972 if (dp->flags & CACHE_FLAG_CANEXIST)
03973 strncat(tmp, "CANEXIST|", sizeof(tmp) - strlen(tmp) - 1);
03974 if (dp->flags & CACHE_FLAG_PENDING)
03975 strncat(tmp, "PENDING|", sizeof(tmp) - strlen(tmp) - 1);
03976 if (dp->flags & CACHE_FLAG_TIMEOUT)
03977 strncat(tmp, "TIMEOUT|", sizeof(tmp) - strlen(tmp) - 1);
03978 if (dp->flags & CACHE_FLAG_TRANSMITTED)
03979 strncat(tmp, "TRANSMITTED|", sizeof(tmp) - strlen(tmp) - 1);
03980 if (dp->flags & CACHE_FLAG_MATCHMORE)
03981 strncat(tmp, "MATCHMORE|", sizeof(tmp) - strlen(tmp) - 1);
03982 if (dp->flags & CACHE_FLAG_UNKNOWN)
03983 strncat(tmp, "UNKNOWN|", sizeof(tmp) - strlen(tmp) - 1);
03984
03985 if (!ast_strlen_zero(tmp)) {
03986 tmp[strlen(tmp) - 1] = '\0';
03987 } else {
03988 ast_copy_string(tmp, "(none)", sizeof(tmp));
03989 }
03990 y = 0;
03991 pc = strchr(dp->peercontext, '@');
03992 if (!pc) {
03993 pc = dp->peercontext;
03994 } else {
03995 pc++;
03996 }
03997 for (x = 0; x < ARRAY_LEN(dp->waiters); x++) {
03998 if (dp->waiters[x] > -1)
03999 y++;
04000 }
04001 if (s > 0) {
04002 ast_cli(a->fd, "%-20.20s %-12.12s %-9d %-8d %s\n", pc, dp->exten, s, y, tmp);
04003 } else {
04004 ast_cli(a->fd, "%-20.20s %-12.12s %-9.9s %-8d %s\n", pc, dp->exten, "(expired)", y, tmp);
04005 }
04006 }
04007
04008 AST_LIST_UNLOCK(&dpcache);
04009
04010 return CLI_SUCCESS;
04011 }
04012
04013 static unsigned int calc_rxstamp(struct chan_iax2_pvt *p, unsigned int offset);
04014
04015 static void unwrap_timestamp(struct iax_frame *fr)
04016 {
04017
04018
04019 const int ts_shift = (fr->af.frametype == AST_FRAME_VIDEO) ? 15 : 16;
04020 const int lower_mask = (1 << ts_shift) - 1;
04021 const int upper_mask = ~lower_mask;
04022 const int last_upper = iaxs[fr->callno]->last & upper_mask;
04023
04024 if ( (fr->ts & upper_mask) == last_upper ) {
04025 const int x = fr->ts - iaxs[fr->callno]->last;
04026 const int threshold = (ts_shift == 15) ? 25000 : 50000;
04027
04028 if (x < -threshold) {
04029
04030
04031
04032
04033 fr->ts = (last_upper + (1 << ts_shift)) | (fr->ts & lower_mask);
04034 if (iaxdebug)
04035 ast_debug(1, "schedule_delivery: pushed forward timestamp\n");
04036 } else if (x > threshold) {
04037
04038
04039
04040
04041 fr->ts = (last_upper - (1 << ts_shift)) | (fr->ts & lower_mask);
04042 if (iaxdebug)
04043 ast_debug(1, "schedule_delivery: pushed back timestamp\n");
04044 }
04045 }
04046 }
04047
04048 static int get_from_jb(const void *p);
04049
04050 static void update_jbsched(struct chan_iax2_pvt *pvt)
04051 {
04052 int when;
04053
04054 when = ast_tvdiff_ms(ast_tvnow(), pvt->rxcore);
04055
04056 when = jb_next(pvt->jb) - when;
04057
04058 if (when <= 0) {
04059
04060 when = 1;
04061 }
04062
04063 pvt->jbid = iax2_sched_replace(pvt->jbid, sched, when, get_from_jb,
04064 CALLNO_TO_PTR(pvt->callno));
04065 }
04066
04067 static void __get_from_jb(const void *p)
04068 {
04069 int callno = PTR_TO_CALLNO(p);
04070 struct chan_iax2_pvt *pvt = NULL;
04071 struct iax_frame *fr;
04072 jb_frame frame;
04073 int ret;
04074 long ms;
04075 long next;
04076 struct timeval now = ast_tvnow();
04077
04078
04079 ast_mutex_lock(&iaxsl[callno]);
04080 pvt = iaxs[callno];
04081 if (!pvt) {
04082
04083 ast_mutex_unlock(&iaxsl[callno]);
04084 return;
04085 }
04086
04087 pvt->jbid = -1;
04088
04089
04090
04091
04092 now.tv_usec += 1000;
04093
04094 ms = ast_tvdiff_ms(now, pvt->rxcore);
04095
04096 if(ms >= (next = jb_next(pvt->jb))) {
04097 ret = jb_get(pvt->jb,&frame,ms,ast_codec_interp_len(pvt->voiceformat));
04098 switch(ret) {
04099 case JB_OK:
04100 fr = frame.data;
04101 __do_deliver(fr);
04102
04103 pvt = iaxs[callno];
04104 break;
04105 case JB_INTERP:
04106 {
04107 struct ast_frame af = { 0, };
04108
04109
04110 af.frametype = AST_FRAME_VOICE;
04111 af.subclass.codec = pvt->voiceformat;
04112 af.samples = frame.ms * (ast_format_rate(pvt->voiceformat) / 1000);
04113 af.src = "IAX2 JB interpolation";
04114 af.delivery = ast_tvadd(pvt->rxcore, ast_samp2tv(next, 1000));
04115 af.offset = AST_FRIENDLY_OFFSET;
04116
04117
04118
04119 if (!ast_test_flag64(iaxs[callno], IAX_ALREADYGONE)) {
04120 iax2_queue_frame(callno, &af);
04121
04122 pvt = iaxs[callno];
04123 }
04124 }
04125 break;
04126 case JB_DROP:
04127 iax2_frame_free(frame.data);
04128 break;
04129 case JB_NOFRAME:
04130 case JB_EMPTY:
04131
04132 break;
04133 default:
04134
04135 break;
04136 }
04137 }
04138 if (pvt)
04139 update_jbsched(pvt);
04140 ast_mutex_unlock(&iaxsl[callno]);
04141 }
04142
04143 static int get_from_jb(const void *data)
04144 {
04145 #ifdef SCHED_MULTITHREADED
04146 if (schedule_action(__get_from_jb, data))
04147 #endif
04148 __get_from_jb(data);
04149 return 0;
04150 }
04151
04152
04153
04154
04155
04156
04157
04158 static int schedule_delivery(struct iax_frame *fr, int updatehistory, int fromtrunk, unsigned int *tsout)
04159 {
04160 int type, len;
04161 int ret;
04162 int needfree = 0;
04163 struct ast_channel *owner = NULL;
04164 struct ast_channel *bridge = NULL;
04165
04166
04167
04168
04169
04170
04171 if (!fr->af.datalen) {
04172 memset(&fr->af.data, 0, sizeof(fr->af.data));
04173 }
04174
04175
04176 unwrap_timestamp(fr);
04177
04178
04179 if ( !fromtrunk && !ast_tvzero(iaxs[fr->callno]->rxcore))
04180 fr->af.delivery = ast_tvadd(iaxs[fr->callno]->rxcore, ast_samp2tv(fr->ts, 1000));
04181 else {
04182 #if 0
04183 ast_debug(1, "schedule_delivery: set delivery to 0 as we don't have an rxcore yet, or frame is from trunk.\n");
04184 #endif
04185 fr->af.delivery = ast_tv(0,0);
04186 }
04187
04188 type = JB_TYPE_CONTROL;
04189 len = 0;
04190
04191 if(fr->af.frametype == AST_FRAME_VOICE) {
04192 type = JB_TYPE_VOICE;
04193 len = ast_codec_get_samples(&fr->af) / (ast_format_rate(fr->af.subclass.codec) / 1000);
04194 } else if(fr->af.frametype == AST_FRAME_CNG) {
04195 type = JB_TYPE_SILENCE;
04196 }
04197
04198 if ( (!ast_test_flag64(iaxs[fr->callno], IAX_USEJITTERBUF)) ) {
04199 if (tsout)
04200 *tsout = fr->ts;
04201 __do_deliver(fr);
04202 return -1;
04203 }
04204
04205 iax2_lock_owner(fr->callno);
04206 if (!iaxs[fr->callno]) {
04207
04208 iax2_frame_free(fr);
04209 return -1;
04210 }
04211 if ((owner = iaxs[fr->callno]->owner))
04212 bridge = ast_bridged_channel(owner);
04213
04214
04215
04216 if ( (!ast_test_flag64(iaxs[fr->callno], IAX_FORCEJITTERBUF)) && owner && bridge && (bridge->tech->properties & AST_CHAN_TP_WANTSJITTER) ) {
04217 jb_frame frame;
04218
04219 ast_channel_unlock(owner);
04220
04221
04222 while (jb_getall(iaxs[fr->callno]->jb, &frame) == JB_OK) {
04223 __do_deliver(frame.data);
04224
04225 if (!iaxs[fr->callno])
04226 return -1;
04227 }
04228
04229 jb_reset(iaxs[fr->callno]->jb);
04230
04231 ast_sched_thread_del(sched, iaxs[fr->callno]->jbid);
04232
04233
04234 if (tsout)
04235 *tsout = fr->ts;
04236 __do_deliver(fr);
04237 return -1;
04238 }
04239 if (owner) {
04240 ast_channel_unlock(owner);
04241 }
04242
04243
04244
04245 ret = jb_put(iaxs[fr->callno]->jb, fr, type, len, fr->ts,
04246 calc_rxstamp(iaxs[fr->callno],fr->ts));
04247 if (ret == JB_DROP) {
04248 needfree++;
04249 } else if (ret == JB_SCHED) {
04250 update_jbsched(iaxs[fr->callno]);
04251 }
04252 if (tsout)
04253 *tsout = fr->ts;
04254 if (needfree) {
04255
04256 iax2_frame_free(fr);
04257 return -1;
04258 }
04259 return 0;
04260 }
04261
04262 static int transmit_frame(void *data)
04263 {
04264 struct iax_frame *fr = data;
04265
04266 ast_mutex_lock(&iaxsl[fr->callno]);
04267
04268 fr->sentyet = 1;
04269
04270 if (iaxs[fr->callno]) {
04271 send_packet(fr);
04272 }
04273
04274 if (fr->retries < 0) {
04275 ast_mutex_unlock(&iaxsl[fr->callno]);
04276
04277 iax_frame_free(fr);
04278 } else {
04279
04280 AST_LIST_INSERT_TAIL(&frame_queue[fr->callno], fr, list);
04281 fr->retries++;
04282 fr->retrans = iax2_sched_add(sched, fr->retrytime, attempt_transmit, fr);
04283 ast_mutex_unlock(&iaxsl[fr->callno]);
04284 }
04285
04286 return 0;
04287 }
04288
04289 static int iax2_transmit(struct iax_frame *fr)
04290 {
04291 fr->sentyet = 0;
04292
04293 return ast_taskprocessor_push(transmit_processor, transmit_frame, fr);
04294 }
04295
04296 static int iax2_digit_begin(struct ast_channel *c, char digit)
04297 {
04298 return send_command_locked(PTR_TO_CALLNO(c->tech_pvt), AST_FRAME_DTMF_BEGIN, digit, 0, NULL, 0, -1);
04299 }
04300
04301 static int iax2_digit_end(struct ast_channel *c, char digit, unsigned int duration)
04302 {
04303 return send_command_locked(PTR_TO_CALLNO(c->tech_pvt), AST_FRAME_DTMF_END, digit, 0, NULL, 0, -1);
04304 }
04305
04306 static int iax2_sendtext(struct ast_channel *c, const char *text)
04307 {
04308
04309 return send_command_locked(PTR_TO_CALLNO(c->tech_pvt), AST_FRAME_TEXT,
04310 0, 0, (unsigned char *)text, strlen(text) + 1, -1);
04311 }
04312
04313 static int iax2_sendimage(struct ast_channel *c, struct ast_frame *img)
04314 {
04315 return send_command_locked(PTR_TO_CALLNO(c->tech_pvt), AST_FRAME_IMAGE, img->subclass.integer, 0, img->data.ptr, img->datalen, -1);
04316 }
04317
04318 static int iax2_sendhtml(struct ast_channel *c, int subclass, const char *data, int datalen)
04319 {
04320 return send_command_locked(PTR_TO_CALLNO(c->tech_pvt), AST_FRAME_HTML, subclass, 0, (unsigned char *)data, datalen, -1);
04321 }
04322
04323 static int iax2_fixup(struct ast_channel *oldchannel, struct ast_channel *newchan)
04324 {
04325 unsigned short callno = PTR_TO_CALLNO(newchan->tech_pvt);
04326 ast_mutex_lock(&iaxsl[callno]);
04327 if (iaxs[callno])
04328 iaxs[callno]->owner = newchan;
04329 else
04330 ast_log(LOG_WARNING, "Uh, this isn't a good sign...\n");
04331 ast_mutex_unlock(&iaxsl[callno]);
04332 return 0;
04333 }
04334
04335
04336
04337
04338
04339 static struct iax2_peer *realtime_peer(const char *peername, struct sockaddr_in *sin)
04340 {
04341 struct ast_variable *var = NULL;
04342 struct ast_variable *tmp;
04343 struct iax2_peer *peer=NULL;
04344 time_t regseconds = 0, nowtime;
04345 int dynamic=0;
04346
04347 if (peername) {
04348 var = ast_load_realtime("iaxpeers", "name", peername, "host", "dynamic", SENTINEL);
04349 if (!var && sin)
04350 var = ast_load_realtime("iaxpeers", "name", peername, "host", ast_inet_ntoa(sin->sin_addr), SENTINEL);
04351 } else if (sin) {
04352 char porta[25];
04353 sprintf(porta, "%d", ntohs(sin->sin_port));
04354 var = ast_load_realtime("iaxpeers", "ipaddr", ast_inet_ntoa(sin->sin_addr), "port", porta, SENTINEL);
04355 if (var) {
04356
04357 for (tmp = var; tmp; tmp = tmp->next) {
04358 if (!strcasecmp(tmp->name, "name"))
04359 peername = tmp->value;
04360 }
04361 }
04362 }
04363 if (!var && peername) {
04364 var = ast_load_realtime("iaxpeers", "name", peername, SENTINEL);
04365
04366
04367
04368
04369
04370
04371 if (var && sin) {
04372 for (tmp = var; tmp; tmp = tmp->next) {
04373 if (!strcasecmp(tmp->name, "host")) {
04374 struct ast_hostent ahp;
04375 struct hostent *hp;
04376 if (!(hp = ast_gethostbyname(tmp->value, &ahp)) || memcmp(hp->h_addr, &sin->sin_addr, hp->h_length)) {
04377
04378 ast_variables_destroy(var);
04379 var = NULL;
04380 }
04381 break;
04382 }
04383 }
04384 }
04385 }
04386 if (!var)
04387 return NULL;
04388
04389 peer = build_peer(peername, var, NULL, ast_test_flag64((&globalflags), IAX_RTCACHEFRIENDS) ? 0 : 1);
04390
04391 if (!peer) {
04392 ast_variables_destroy(var);
04393 return NULL;
04394 }
04395
04396 for (tmp = var; tmp; tmp = tmp->next) {
04397
04398 if (!strcasecmp(tmp->name, "type")) {
04399 if (strcasecmp(tmp->value, "friend") &&
04400 strcasecmp(tmp->value, "peer")) {
04401
04402 peer = peer_unref(peer);
04403 break;
04404 }
04405 } else if (!strcasecmp(tmp->name, "regseconds")) {
04406 ast_get_time_t(tmp->value, ®seconds, 0, NULL);
04407 } else if (!strcasecmp(tmp->name, "ipaddr")) {
04408 if (!ast_sockaddr_parse(&peer->addr, tmp->value, PARSE_PORT_IGNORE)) {
04409 ast_log(LOG_WARNING, "Failed to parse sockaddr '%s' for ipaddr of realtime peer '%s'\n", tmp->value, tmp->name);
04410 }
04411 } else if (!strcasecmp(tmp->name, "port")) {
04412 ast_sockaddr_set_port(&peer->addr, atoi(tmp->value));
04413 } else if (!strcasecmp(tmp->name, "host")) {
04414 if (!strcasecmp(tmp->value, "dynamic"))
04415 dynamic = 1;
04416 }
04417 }
04418
04419 ast_variables_destroy(var);
04420
04421 if (!peer)
04422 return NULL;
04423
04424 if (ast_test_flag64((&globalflags), IAX_RTCACHEFRIENDS)) {
04425 ast_copy_flags64(peer, &globalflags, IAX_RTAUTOCLEAR|IAX_RTCACHEFRIENDS);
04426 if (ast_test_flag64(peer, IAX_RTAUTOCLEAR)) {
04427 if (peer->expire > -1) {
04428 if (!ast_sched_thread_del(sched, peer->expire)) {
04429 peer->expire = -1;
04430 peer_unref(peer);
04431 }
04432 }
04433 peer->expire = iax2_sched_add(sched, (global_rtautoclear) * 1000, expire_registry, peer_ref(peer));
04434 if (peer->expire == -1)
04435 peer_unref(peer);
04436 }
04437 ao2_link(peers, peer);
04438 if (ast_test_flag64(peer, IAX_DYNAMIC))
04439 reg_source_db(peer);
04440 } else {
04441 ast_set_flag64(peer, IAX_TEMPONLY);
04442 }
04443
04444 if (!ast_test_flag64(&globalflags, IAX_RTIGNOREREGEXPIRE) && dynamic) {
04445 time(&nowtime);
04446 if ((nowtime - regseconds) > IAX_DEFAULT_REG_EXPIRE) {
04447 memset(&peer->addr, 0, sizeof(peer->addr));
04448 realtime_update_peer(peer->name, &peer->addr, 0);
04449 ast_debug(1, "realtime_peer: Bah, '%s' is expired (%d/%d/%d)!\n",
04450 peername, (int)(nowtime - regseconds), (int)regseconds, (int)nowtime);
04451 }
04452 else {
04453 ast_debug(1, "realtime_peer: Registration for '%s' still active (%d/%d/%d)!\n",
04454 peername, (int)(nowtime - regseconds), (int)regseconds, (int)nowtime);
04455 }
04456 }
04457
04458 return peer;
04459 }
04460
04461 static struct iax2_user *realtime_user(const char *username, struct sockaddr_in *sin)
04462 {
04463 struct ast_variable *var;
04464 struct ast_variable *tmp;
04465 struct iax2_user *user=NULL;
04466
04467 var = ast_load_realtime("iaxusers", "name", username, "host", "dynamic", SENTINEL);
04468 if (!var)
04469 var = ast_load_realtime("iaxusers", "name", username, "host", ast_inet_ntoa(sin->sin_addr), SENTINEL);
04470 if (!var && sin) {
04471 char porta[6];
04472 snprintf(porta, sizeof(porta), "%d", ntohs(sin->sin_port));
04473 var = ast_load_realtime("iaxusers", "name", username, "ipaddr", ast_inet_ntoa(sin->sin_addr), "port", porta, SENTINEL);
04474 if (!var)
04475 var = ast_load_realtime("iaxusers", "ipaddr", ast_inet_ntoa(sin->sin_addr), "port", porta, SENTINEL);
04476 }
04477 if (!var) {
04478 var = ast_load_realtime("iaxusers", "name", username, SENTINEL);
04479
04480
04481
04482
04483
04484
04485 if (var) {
04486 for (tmp = var; tmp; tmp = tmp->next) {
04487 if (!strcasecmp(tmp->name, "host")) {
04488 struct ast_hostent ahp;
04489 struct hostent *hp;
04490 if (!(hp = ast_gethostbyname(tmp->value, &ahp)) || memcmp(hp->h_addr, &sin->sin_addr, hp->h_length)) {
04491
04492 ast_variables_destroy(var);
04493 var = NULL;
04494 }
04495 break;
04496 }
04497 }
04498 }
04499 }
04500 if (!var)
04501 return NULL;
04502
04503 tmp = var;
04504 while(tmp) {
04505
04506 if (!strcasecmp(tmp->name, "type")) {
04507 if (strcasecmp(tmp->value, "friend") &&
04508 strcasecmp(tmp->value, "user")) {
04509 return NULL;
04510 }
04511 }
04512 tmp = tmp->next;
04513 }
04514
04515 user = build_user(username, var, NULL, !ast_test_flag64((&globalflags), IAX_RTCACHEFRIENDS));
04516
04517 ast_variables_destroy(var);
04518
04519 if (!user)
04520 return NULL;
04521
04522 if (ast_test_flag64((&globalflags), IAX_RTCACHEFRIENDS)) {
04523 ast_set_flag64(user, IAX_RTCACHEFRIENDS);
04524 ao2_link(users, user);
04525 } else {
04526 ast_set_flag64(user, IAX_TEMPONLY);
04527 }
04528
04529 return user;
04530 }
04531
04532 static void realtime_update_peer(const char *peername, struct ast_sockaddr *sockaddr, time_t regtime)
04533 {
04534 char port[10];
04535 char regseconds[20];
04536 const char *sysname = ast_config_AST_SYSTEM_NAME;
04537 char *syslabel = NULL;
04538
04539 if (ast_strlen_zero(sysname))
04540 sysname = NULL;
04541 else if (ast_test_flag64(&globalflags, IAX_RTSAVE_SYSNAME))
04542 syslabel = "regserver";
04543
04544 snprintf(regseconds, sizeof(regseconds), "%d", (int)regtime);
04545 snprintf(port, sizeof(port), "%d", ast_sockaddr_port(sockaddr));
04546 ast_update_realtime("iaxpeers", "name", peername,
04547 "ipaddr", ast_sockaddr_stringify_addr(sockaddr), "port", port,
04548 "regseconds", regseconds, syslabel, sysname, SENTINEL);
04549 }
04550
04551 struct create_addr_info {
04552 format_t capability;
04553 uint64_t flags;
04554 int maxtime;
04555 int encmethods;
04556 int found;
04557 int sockfd;
04558 int adsi;
04559 char username[80];
04560 char secret[80];
04561 char outkey[80];
04562 char timezone[80];
04563 char prefs[32];
04564 char cid_num[80];
04565 char cid_name[80];
04566 char context[AST_MAX_CONTEXT];
04567 char peercontext[AST_MAX_CONTEXT];
04568 char mohinterpret[MAX_MUSICCLASS];
04569 char mohsuggest[MAX_MUSICCLASS];
04570 };
04571
04572 static int create_addr(const char *peername, struct ast_channel *c, struct sockaddr_in *sin, struct create_addr_info *cai)
04573 {
04574 struct iax2_peer *peer;
04575 int res = -1;
04576 struct ast_codec_pref ourprefs;
04577 struct sockaddr_in peer_addr;
04578
04579 ast_clear_flag64(cai, IAX_SENDANI | IAX_TRUNK);
04580 cai->sockfd = defaultsockfd;
04581 cai->maxtime = 0;
04582 sin->sin_family = AF_INET;
04583
04584 if (!(peer = find_peer(peername, 1))) {
04585 struct ast_sockaddr sin_tmp;
04586
04587 cai->found = 0;
04588 sin_tmp.ss.ss_family = AF_INET;
04589 if (ast_get_ip_or_srv(&sin_tmp, peername, srvlookup ? "_iax._udp" : NULL)) {
04590 ast_log(LOG_WARNING, "No such host: %s\n", peername);
04591 return -1;
04592 }
04593 ast_sockaddr_to_sin(&sin_tmp, sin);
04594 if (sin->sin_port == 0) {
04595 sin->sin_port = htons(IAX_DEFAULT_PORTNO);
04596 }
04597
04598
04599 memcpy(&ourprefs, &prefs, sizeof(ourprefs));
04600 if (c)
04601 ast_codec_pref_prepend(&ourprefs, c->nativeformats, 1);
04602 ast_codec_pref_convert(&ourprefs, cai->prefs, sizeof(cai->prefs), 1);
04603 return 0;
04604 }
04605
04606 cai->found = 1;
04607
04608 ast_sockaddr_to_sin(&peer->addr, &peer_addr);
04609
04610
04611 if (!(peer_addr.sin_addr.s_addr || peer->defaddr.sin_addr.s_addr)) {
04612 goto return_unref;
04613 }
04614
04615
04616 if (peer->maxms && ((peer->lastms > peer->maxms) || (peer->lastms < 0)))
04617 goto return_unref;
04618
04619 ast_copy_flags64(cai, peer, IAX_SENDANI | IAX_TRUNK | IAX_NOTRANSFER | IAX_TRANSFERMEDIA | IAX_USEJITTERBUF | IAX_FORCEJITTERBUF | IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE | IAX_FORCE_ENCRYPT);
04620 cai->maxtime = peer->maxms;
04621 cai->capability = peer->capability;
04622 cai->encmethods = peer->encmethods;
04623 cai->sockfd = peer->sockfd;
04624 cai->adsi = peer->adsi;
04625 memcpy(&ourprefs, &peer->prefs, sizeof(ourprefs));
04626
04627 if (c) {
04628 ast_debug(1, "prepending %llx to prefs\n", (unsigned long long) c->nativeformats);
04629 ast_codec_pref_prepend(&ourprefs, c->nativeformats, 1);
04630 }
04631 ast_codec_pref_convert(&ourprefs, cai->prefs, sizeof(cai->prefs), 1);
04632 ast_copy_string(cai->context, peer->context, sizeof(cai->context));
04633 ast_copy_string(cai->peercontext, peer->peercontext, sizeof(cai->peercontext));
04634 ast_copy_string(cai->username, peer->username, sizeof(cai->username));
04635 ast_copy_string(cai->timezone, peer->zonetag, sizeof(cai->timezone));
04636 ast_copy_string(cai->outkey, peer->outkey, sizeof(cai->outkey));
04637 ast_copy_string(cai->cid_num, peer->cid_num, sizeof(cai->cid_num));
04638 ast_copy_string(cai->cid_name, peer->cid_name, sizeof(cai->cid_name));
04639 ast_copy_string(cai->mohinterpret, peer->mohinterpret, sizeof(cai->mohinterpret));
04640 ast_copy_string(cai->mohsuggest, peer->mohsuggest, sizeof(cai->mohsuggest));
04641 if (ast_strlen_zero(peer->dbsecret)) {
04642 ast_copy_string(cai->secret, peer->secret, sizeof(cai->secret));
04643 } else {
04644 char *family;
04645 char *key = NULL;
04646
04647 family = ast_strdupa(peer->dbsecret);
04648 key = strchr(family, '/');
04649 if (key)
04650 *key++ = '\0';
04651 if (!key || ast_db_get(family, key, cai->secret, sizeof(cai->secret))) {
04652 ast_log(LOG_WARNING, "Unable to retrieve database password for family/key '%s'!\n", peer->dbsecret);
04653 goto return_unref;
04654 }
04655 }
04656
04657 if (peer_addr.sin_addr.s_addr) {
04658 sin->sin_addr = peer_addr.sin_addr;
04659 sin->sin_port = peer_addr.sin_port;
04660 } else {
04661 sin->sin_addr = peer->defaddr.sin_addr;
04662 sin->sin_port = peer->defaddr.sin_port;
04663 }
04664
04665 res = 0;
04666
04667 return_unref:
04668 peer_unref(peer);
04669
04670 return res;
04671 }
04672
04673 static void __auto_congest(const void *nothing)
04674 {
04675 int callno = PTR_TO_CALLNO(nothing);
04676 struct ast_frame f = { AST_FRAME_CONTROL, { AST_CONTROL_CONGESTION } };
04677 ast_mutex_lock(&iaxsl[callno]);
04678 if (iaxs[callno]) {
04679 iaxs[callno]->initid = -1;
04680 iax2_queue_frame(callno, &f);
04681 ast_log(LOG_NOTICE, "Auto-congesting call due to slow response\n");
04682 }
04683 ast_mutex_unlock(&iaxsl[callno]);
04684 }
04685
04686 static int auto_congest(const void *data)
04687 {
04688 #ifdef SCHED_MULTITHREADED
04689 if (schedule_action(__auto_congest, data))
04690 #endif
04691 __auto_congest(data);
04692 return 0;
04693 }
04694
04695 static unsigned int iax2_datetime(const char *tz)
04696 {
04697 struct timeval t = ast_tvnow();
04698 struct ast_tm tm;
04699 unsigned int tmp;
04700 ast_localtime(&t, &tm, ast_strlen_zero(tz) ? NULL : tz);
04701 tmp = (tm.tm_sec >> 1) & 0x1f;
04702 tmp |= (tm.tm_min & 0x3f) << 5;
04703 tmp |= (tm.tm_hour & 0x1f) << 11;
04704 tmp |= (tm.tm_mday & 0x1f) << 16;
04705 tmp |= ((tm.tm_mon + 1) & 0xf) << 21;
04706 tmp |= ((tm.tm_year - 100) & 0x7f) << 25;
04707 return tmp;
04708 }
04709
04710 struct parsed_dial_string {
04711 char *username;
04712 char *password;
04713 char *key;
04714 char *peer;
04715 char *port;
04716 char *exten;
04717 char *context;
04718 char *options;
04719 };
04720
04721 static int send_apathetic_reply(unsigned short callno, unsigned short dcallno,
04722 struct sockaddr_in *sin, int command, int ts, unsigned char seqno,
04723 int sockfd, struct iax_ie_data *ied)
04724 {
04725 struct {
04726 struct ast_iax2_full_hdr f;
04727 struct iax_ie_data ied;
04728 } data;
04729 size_t size = sizeof(struct ast_iax2_full_hdr);
04730
04731 if (ied) {
04732 size += ied->pos;
04733 memcpy(&data.ied, ied->buf, ied->pos);
04734 }
04735
04736 data.f.scallno = htons(0x8000 | callno);
04737 data.f.dcallno = htons(dcallno & ~IAX_FLAG_RETRANS);
04738 data.f.ts = htonl(ts);
04739 data.f.iseqno = seqno;
04740 data.f.oseqno = 0;
04741 data.f.type = AST_FRAME_IAX;
04742 data.f.csub = compress_subclass(command);
04743
04744 if (iaxdebug) {
04745 iax_outputframe(NULL, &data.f, 0, sin, size - sizeof(struct ast_iax2_full_hdr));
04746 }
04747
04748 return sendto(sockfd, &data, size, 0, (struct sockaddr *)sin, sizeof(*sin));
04749 }
04750
04751 static void add_empty_calltoken_ie(struct chan_iax2_pvt *pvt, struct iax_ie_data *ied)
04752 {
04753
04754 if (pvt && ied && (2 < ((int) sizeof(ied->buf) - ied->pos))) {
04755 ied->buf[ied->pos++] = IAX_IE_CALLTOKEN;
04756 ied->buf[ied->pos++] = 0;
04757 pvt->calltoken_ie_len = 2;
04758 }
04759 }
04760
04761 static void resend_with_token(int callno, struct iax_frame *f, const char *newtoken)
04762 {
04763 struct chan_iax2_pvt *pvt = iaxs[callno];
04764 int frametype = f->af.frametype;
04765 int subclass = f->af.subclass.integer;
04766 struct {
04767 struct ast_iax2_full_hdr fh;
04768 struct iax_ie_data ied;
04769 } data = {
04770 .ied.buf = { 0 },
04771 .ied.pos = 0,
04772 };
04773
04774 int ie_data_pos = f->datalen - sizeof(struct ast_iax2_full_hdr);
04775
04776 if (!pvt) {
04777 return;
04778 }
04779
04780
04781
04782
04783
04784
04785
04786
04787
04788
04789
04790
04791 if (f->encmethods || f->dcallno || !iax2_allow_new(frametype, subclass, 0)
04792 || !pvt->calltoken_ie_len || (pvt->calltoken_ie_len > ie_data_pos) ||
04793 (f->datalen > sizeof(data))) {
04794
04795 return;
04796 }
04797
04798
04799
04800
04801
04802
04803
04804
04805
04806
04807
04808
04809
04810
04811
04812 memcpy(&data, f->data, f->datalen);
04813 data.ied.pos = ie_data_pos;
04814
04815
04816
04817 data.ied.pos -= pvt->calltoken_ie_len;
04818 iax_ie_append_str(&data.ied, IAX_IE_CALLTOKEN, newtoken);
04819
04820
04821 pvt->calltoken_ie_len = data.ied.pos - ie_data_pos;
04822
04823
04824 AST_LIST_REMOVE(&frame_queue[callno], f, list);
04825
04826
04827 iax2_frame_free(f);
04828
04829
04830 pvt->oseqno = 0;
04831 pvt->rseqno = 0;
04832 pvt->iseqno = 0;
04833 pvt->aseqno = 0;
04834 if (pvt->peercallno) {
04835 remove_by_peercallno(pvt);
04836 pvt->peercallno = 0;
04837 }
04838
04839
04840 send_command(pvt, AST_FRAME_IAX, subclass, 0, data.ied.buf, data.ied.pos, -1);
04841 }
04842
04843 static void requirecalltoken_mark_auto(const char *name, int subclass)
04844 {
04845 struct iax2_user *user = NULL;
04846 struct iax2_peer *peer = NULL;
04847
04848 if (ast_strlen_zero(name)) {
04849 return;
04850 }
04851
04852 if ((subclass == IAX_COMMAND_NEW) && (user = find_user(name)) && (user->calltoken_required == CALLTOKEN_AUTO)) {
04853 user->calltoken_required = CALLTOKEN_YES;
04854 } else if ((subclass != IAX_COMMAND_NEW) && (peer = find_peer(name, 1)) && (peer->calltoken_required == CALLTOKEN_AUTO)) {
04855 peer->calltoken_required = CALLTOKEN_YES;
04856 }
04857
04858 if (peer) {
04859 peer_unref(peer);
04860 }
04861 if (user) {
04862 user_unref(user);
04863 }
04864 }
04865
04866
04867
04868
04869
04870
04871
04872
04873
04874
04875
04876
04877
04878
04879
04880
04881
04882
04883 static int handle_call_token(struct ast_iax2_full_hdr *fh, struct iax_ies *ies,
04884 struct sockaddr_in *sin, int fd)
04885 {
04886 #define CALLTOKEN_HASH_FORMAT "%s%d%u%d"
04887 #define CALLTOKEN_IE_FORMAT "%u?%s"
04888 struct ast_str *buf = ast_str_alloca(256);
04889 time_t t = time(NULL);
04890 char hash[41];
04891 int subclass = uncompress_subclass(fh->csub);
04892
04893
04894 if (ies->calltoken && !ies->calltokendata) {
04895 struct iax_ie_data ied = {
04896 .buf = { 0 },
04897 .pos = 0,
04898 };
04899
04900
04901 ast_str_set(&buf, 0, CALLTOKEN_HASH_FORMAT, ast_inet_ntoa(sin->sin_addr), sin->sin_port, (unsigned int) t, randomcalltokendata);
04902 ast_sha1_hash(hash, ast_str_buffer(buf));
04903
04904 ast_str_set(&buf, 0, CALLTOKEN_IE_FORMAT, (unsigned int) t, hash);
04905 iax_ie_append_str(&ied, IAX_IE_CALLTOKEN, ast_str_buffer(buf));
04906 send_apathetic_reply(1, ntohs(fh->scallno), sin, IAX_COMMAND_CALLTOKEN, ntohl(fh->ts), fh->iseqno + 1, fd, &ied);
04907
04908 return 1;
04909
04910
04911 } else if (ies->calltoken && ies->calltokendata) {
04912 char *rec_hash = NULL;
04913 char *rec_ts = NULL;
04914 unsigned int rec_time;
04915
04916
04917 rec_hash = strchr((char *) ies->calltokendata, '?');
04918 if (rec_hash) {
04919 *rec_hash++ = '\0';
04920 rec_ts = (char *) ies->calltokendata;
04921 }
04922
04923
04924 if (!rec_hash || !rec_ts) {
04925 goto reject;
04926 } else if (sscanf(rec_ts, "%u", &rec_time) != 1) {
04927 goto reject;
04928 }
04929
04930
04931 ast_str_set(&buf, 0, CALLTOKEN_HASH_FORMAT, ast_inet_ntoa(sin->sin_addr), sin->sin_port, (unsigned int) rec_time, randomcalltokendata);
04932 ast_sha1_hash(hash, ast_str_buffer(buf));
04933
04934
04935 if (strcmp(hash, rec_hash)) {
04936 ast_log(LOG_WARNING, "Address %s failed CallToken hash inspection\n", ast_inet_ntoa(sin->sin_addr));
04937 goto reject;
04938 } else if ((t < rec_time) || ((t - rec_time) >= MAX_CALLTOKEN_DELAY)) {
04939 ast_log(LOG_WARNING, "Too much delay in IAX2 calltoken timestamp from address %s\n", ast_inet_ntoa(sin->sin_addr));
04940 goto reject;
04941 }
04942
04943
04944
04945 requirecalltoken_mark_auto(ies->username, subclass);
04946 return 0;
04947
04948
04949 } else {
04950 if (calltoken_required(sin, ies->username, subclass)) {
04951 ast_log(LOG_ERROR, "Call rejected, CallToken Support required. If unexpected, resolve by placing address %s in the calltokenoptional list or setting user %s requirecalltoken=no\n", ast_inet_ntoa(sin->sin_addr), S_OR(ies->username, "guest"));
04952 goto reject;
04953 }
04954 return 0;
04955 }
04956
04957 reject:
04958
04959 if (subclass == IAX_COMMAND_REGREQ || subclass == IAX_COMMAND_REGREL) {
04960 send_apathetic_reply(1, ntohs(fh->scallno), sin, IAX_COMMAND_REGREJ, ntohl(fh->ts), fh->iseqno + 1, fd, NULL);
04961 } else {
04962 send_apathetic_reply(1, ntohs(fh->scallno), sin, IAX_COMMAND_REJECT, ntohl(fh->ts), fh->iseqno + 1, fd, NULL);
04963 }
04964
04965 return 1;
04966 }
04967
04968
04969
04970
04971
04972
04973
04974
04975
04976
04977
04978
04979
04980
04981
04982
04983
04984
04985
04986 static void parse_dial_string(char *data, struct parsed_dial_string *pds)
04987 {
04988 if (ast_strlen_zero(data))
04989 return;
04990
04991 pds->peer = strsep(&data, "/");
04992 pds->exten = strsep(&data, "/");
04993 pds->options = data;
04994
04995 if (pds->exten) {
04996 data = pds->exten;
04997 pds->exten = strsep(&data, "@");
04998 pds->context = data;
04999 }
05000
05001 if (strchr(pds->peer, '@')) {
05002 data = pds->peer;
05003 pds->username = strsep(&data, "@");
05004 pds->peer = data;
05005 }
05006
05007 if (pds->username) {
05008 data = pds->username;
05009 pds->username = strsep(&data, ":");
05010 pds->password = data;
05011 }
05012
05013 data = pds->peer;
05014 pds->peer = strsep(&data, ":");
05015 pds->port = data;
05016
05017
05018
05019
05020 if (pds->password && (pds->password[0] == '[')) {
05021 pds->key = ast_strip_quoted(pds->password, "[", "]");
05022 pds->password = NULL;
05023 }
05024 }
05025
05026 static int iax2_call(struct ast_channel *c, char *dest, int timeout)
05027 {
05028 struct sockaddr_in sin;
05029 char *l=NULL, *n=NULL, *tmpstr;
05030 struct iax_ie_data ied;
05031 char *defaultrdest = "s";
05032 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
05033 struct parsed_dial_string pds;
05034 struct create_addr_info cai;
05035 struct ast_var_t *var;
05036 struct ast_datastore *variablestore = ast_channel_datastore_find(c, &iax2_variable_datastore_info, NULL);
05037 const char* osp_token_ptr;
05038 unsigned int osp_token_length;
05039 unsigned char osp_block_index;
05040 unsigned int osp_block_length;
05041 unsigned char osp_buffer[256];
05042
05043 if ((c->_state != AST_STATE_DOWN) && (c->_state != AST_STATE_RESERVED)) {
05044 ast_log(LOG_WARNING, "Channel is already in use (%s)?\n", c->name);
05045 return -1;
05046 }
05047
05048 memset(&cai, 0, sizeof(cai));
05049 cai.encmethods = iax2_encryption;
05050
05051 memset(&pds, 0, sizeof(pds));
05052 tmpstr = ast_strdupa(dest);
05053 parse_dial_string(tmpstr, &pds);
05054
05055 if (ast_strlen_zero(pds.peer)) {
05056 ast_log(LOG_WARNING, "No peer provided in the IAX2 dial string '%s'\n", dest);
05057 return -1;
05058 }
05059 if (!pds.exten) {
05060 pds.exten = defaultrdest;
05061 }
05062 if (create_addr(pds.peer, c, &sin, &cai)) {
05063 ast_log(LOG_WARNING, "No address associated with '%s'\n", pds.peer);
05064 return -1;
05065 }
05066 if (ast_test_flag64(iaxs[callno], IAX_FORCE_ENCRYPT) && !cai.encmethods) {
05067 ast_log(LOG_WARNING, "Encryption forced for call, but not enabled\n");
05068 c->hangupcause = AST_CAUSE_BEARERCAPABILITY_NOTAVAIL;
05069 return -1;
05070 }
05071 if (ast_strlen_zero(cai.secret) && ast_test_flag64(iaxs[callno], IAX_FORCE_ENCRYPT)) {
05072 ast_log(LOG_WARNING, "Call terminated. No secret given and force encrypt enabled\n");
05073 return -1;
05074 }
05075 if (!pds.username && !ast_strlen_zero(cai.username))
05076 pds.username = cai.username;
05077 if (!pds.password && !ast_strlen_zero(cai.secret))
05078 pds.password = cai.secret;
05079 if (!pds.key && !ast_strlen_zero(cai.outkey))
05080 pds.key = cai.outkey;
05081 if (!pds.context && !ast_strlen_zero(cai.peercontext))
05082 pds.context = cai.peercontext;
05083
05084
05085 ast_copy_string(c->context, cai.context, sizeof(c->context));
05086
05087 if (pds.port)
05088 sin.sin_port = htons(atoi(pds.port));
05089
05090 l = c->connected.id.number.valid ? c->connected.id.number.str : NULL;
05091 n = c->connected.id.name.valid ? c->connected.id.name.str : NULL;
05092
05093
05094 memset(&ied, 0, sizeof(ied));
05095
05096
05097 iax_ie_append_short(&ied, IAX_IE_VERSION, IAX_PROTO_VERSION);
05098 iax_ie_append_str(&ied, IAX_IE_CALLED_NUMBER, pds.exten);
05099 if (pds.options && strchr(pds.options, 'a')) {
05100
05101 iax_ie_append(&ied, IAX_IE_AUTOANSWER);
05102 }
05103
05104
05105 iax_ie_append_str(&ied, IAX_IE_CODEC_PREFS, cai.prefs);
05106
05107 if (l) {
05108 iax_ie_append_str(&ied, IAX_IE_CALLING_NUMBER, l);
05109 iax_ie_append_byte(&ied, IAX_IE_CALLINGPRES,
05110 ast_party_id_presentation(&c->connected.id));
05111 } else if (n) {
05112 iax_ie_append_byte(&ied, IAX_IE_CALLINGPRES,
05113 ast_party_id_presentation(&c->connected.id));
05114 } else {
05115 iax_ie_append_byte(&ied, IAX_IE_CALLINGPRES, AST_PRES_NUMBER_NOT_AVAILABLE);
05116 }
05117
05118 iax_ie_append_byte(&ied, IAX_IE_CALLINGTON, c->connected.id.number.plan);
05119 iax_ie_append_short(&ied, IAX_IE_CALLINGTNS, c->dialed.transit_network_select);
05120
05121 if (n)
05122 iax_ie_append_str(&ied, IAX_IE_CALLING_NAME, n);
05123 if (ast_test_flag64(iaxs[callno], IAX_SENDANI)
05124 && c->connected.ani.number.valid
05125 && c->connected.ani.number.str) {
05126 iax_ie_append_str(&ied, IAX_IE_CALLING_ANI, c->connected.ani.number.str);
05127 }
05128
05129 if (!ast_strlen_zero(c->language))
05130 iax_ie_append_str(&ied, IAX_IE_LANGUAGE, c->language);
05131 if (!ast_strlen_zero(c->dialed.number.str)) {
05132 iax_ie_append_str(&ied, IAX_IE_DNID, c->dialed.number.str);
05133 }
05134 if (c->redirecting.from.number.valid
05135 && !ast_strlen_zero(c->redirecting.from.number.str)) {
05136 iax_ie_append_str(&ied, IAX_IE_RDNIS, c->redirecting.from.number.str);
05137 }
05138
05139 if (pds.context)
05140 iax_ie_append_str(&ied, IAX_IE_CALLED_CONTEXT, pds.context);
05141
05142 if (pds.username)
05143 iax_ie_append_str(&ied, IAX_IE_USERNAME, pds.username);
05144
05145 if (cai.encmethods)
05146 iax_ie_append_short(&ied, IAX_IE_ENCRYPTION, cai.encmethods);
05147
05148 ast_mutex_lock(&iaxsl[callno]);
05149
05150 if (!ast_strlen_zero(c->context))
05151 ast_string_field_set(iaxs[callno], context, c->context);
05152
05153 if (pds.username)
05154 ast_string_field_set(iaxs[callno], username, pds.username);
05155
05156 iaxs[callno]->encmethods = cai.encmethods;
05157
05158 iaxs[callno]->adsi = cai.adsi;
05159
05160 ast_string_field_set(iaxs[callno], mohinterpret, cai.mohinterpret);
05161 ast_string_field_set(iaxs[callno], mohsuggest, cai.mohsuggest);
05162
05163 if (pds.key)
05164 ast_string_field_set(iaxs[callno], outkey, pds.key);
05165 if (pds.password)
05166 ast_string_field_set(iaxs[callno], secret, pds.password);
05167
05168 iax_ie_append_int(&ied, IAX_IE_FORMAT, (int) c->nativeformats);
05169 iax_ie_append_versioned_uint64(&ied, IAX_IE_FORMAT2, 0, c->nativeformats);
05170 iax_ie_append_int(&ied, IAX_IE_CAPABILITY, (int) iaxs[callno]->capability);
05171 iax_ie_append_versioned_uint64(&ied, IAX_IE_CAPABILITY2, 0, iaxs[callno]->capability);
05172 iax_ie_append_short(&ied, IAX_IE_ADSICPE, c->adsicpe);
05173 iax_ie_append_int(&ied, IAX_IE_DATETIME, iax2_datetime(cai.timezone));
05174
05175 if (iaxs[callno]->maxtime) {
05176
05177 iaxs[callno]->pingtime = iaxs[callno]->maxtime / 2;
05178 iaxs[callno]->initid = iax2_sched_add(sched, iaxs[callno]->maxtime * 2, auto_congest, CALLNO_TO_PTR(callno));
05179 } else if (autokill) {
05180 iaxs[callno]->pingtime = autokill / 2;
05181 iaxs[callno]->initid = iax2_sched_add(sched, autokill * 2, auto_congest, CALLNO_TO_PTR(callno));
05182 }
05183
05184
05185 osp_token_ptr = pbx_builtin_getvar_helper(c, "IAX2OSPTOKEN");
05186 if (!ast_strlen_zero(osp_token_ptr)) {
05187 if ((osp_token_length = strlen(osp_token_ptr)) <= IAX_MAX_OSPTOKEN_SIZE) {
05188 osp_block_index = 0;
05189 while (osp_token_length > 0) {
05190 osp_block_length = IAX_MAX_OSPBLOCK_SIZE < osp_token_length ? IAX_MAX_OSPBLOCK_SIZE : osp_token_length;
05191 osp_buffer[0] = osp_block_index;
05192 memcpy(osp_buffer + 1, osp_token_ptr, osp_block_length);
05193 iax_ie_append_raw(&ied, IAX_IE_OSPTOKEN, osp_buffer, osp_block_length + 1);
05194 osp_block_index++;
05195 osp_token_ptr += osp_block_length;
05196 osp_token_length -= osp_block_length;
05197 }
05198 } else
05199 ast_log(LOG_WARNING, "OSP token is too long\n");
05200 } else if (iaxdebug)
05201 ast_debug(1, "OSP token is undefined\n");
05202
05203
05204 iaxs[callno]->sockfd = cai.sockfd;
05205
05206
05207 if (variablestore) {
05208 AST_LIST_HEAD(, ast_var_t) *variablelist = variablestore->data;
05209 ast_debug(1, "Found an IAX variable store on this channel\n");
05210 AST_LIST_LOCK(variablelist);
05211 AST_LIST_TRAVERSE(variablelist, var, entries) {
05212 char tmp[256];
05213 int i;
05214 ast_debug(1, "Found IAXVAR '%s' with value '%s' (to transmit)\n", ast_var_name(var), ast_var_value(var));
05215
05216 for (i = 0; i < strlen(ast_var_value(var)); i += 255 - (strlen(ast_var_name(var)) + 1)) {
05217 snprintf(tmp, sizeof(tmp), "%s=%s", ast_var_name(var), ast_var_value(var) + i);
05218 iax_ie_append_str(&ied, IAX_IE_VARIABLE, tmp);
05219 }
05220 }
05221 AST_LIST_UNLOCK(variablelist);
05222 }
05223
05224
05225 add_empty_calltoken_ie(iaxs[callno], &ied);
05226 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_NEW, 0, ied.buf, ied.pos, -1);
05227
05228 ast_mutex_unlock(&iaxsl[callno]);
05229 ast_setstate(c, AST_STATE_RINGING);
05230
05231 return 0;
05232 }
05233
05234 static int iax2_hangup(struct ast_channel *c)
05235 {
05236 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
05237 struct iax_ie_data ied;
05238 int alreadygone;
05239 memset(&ied, 0, sizeof(ied));
05240 ast_mutex_lock(&iaxsl[callno]);
05241 if (callno && iaxs[callno]) {
05242 ast_debug(1, "We're hanging up %s now...\n", c->name);
05243 alreadygone = ast_test_flag64(iaxs[callno], IAX_ALREADYGONE);
05244
05245 iax_ie_append_byte(&ied, IAX_IE_CAUSECODE, (unsigned char)c->hangupcause);
05246 if (!iaxs[callno]->error && !alreadygone) {
05247 if (send_command_final(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_HANGUP, 0, ied.buf, ied.pos, -1)) {
05248 ast_log(LOG_WARNING, "No final packet could be sent for callno %d\n", callno);
05249 }
05250 if (!iaxs[callno]) {
05251 ast_mutex_unlock(&iaxsl[callno]);
05252 return 0;
05253 }
05254 }
05255
05256 iax2_predestroy(callno);
05257
05258 if (iaxs[callno] && alreadygone) {
05259 ast_debug(1, "Really destroying %s now...\n", c->name);
05260 iax2_destroy(callno);
05261 } else if (iaxs[callno]) {
05262 if (ast_sched_thread_add(sched, 10000, scheduled_destroy, CALLNO_TO_PTR(callno)) < 0) {
05263 ast_log(LOG_ERROR, "Unable to schedule iax2 callno %d destruction?!! Destroying immediately.\n", callno);
05264 iax2_destroy(callno);
05265 }
05266 }
05267 } else if (c->tech_pvt) {
05268
05269
05270
05271
05272 c->tech_pvt = NULL;
05273 }
05274 ast_mutex_unlock(&iaxsl[callno]);
05275 ast_verb(3, "Hungup '%s'\n", c->name);
05276 return 0;
05277 }
05278
05279
05280
05281
05282 static int wait_for_peercallno(struct chan_iax2_pvt *pvt)
05283 {
05284 unsigned short callno = pvt->callno;
05285
05286 if (!pvt->peercallno) {
05287
05288 int count = 10;
05289 while (count-- && pvt && !pvt->peercallno) {
05290 DEADLOCK_AVOIDANCE(&iaxsl[callno]);
05291 pvt = iaxs[callno];
05292 }
05293 if (!pvt || !pvt->peercallno) {
05294 return -1;
05295 }
05296 }
05297
05298 return 0;
05299 }
05300
05301 static int iax2_setoption(struct ast_channel *c, int option, void *data, int datalen)
05302 {
05303 struct ast_option_header *h;
05304 int res;
05305
05306 switch (option) {
05307 case AST_OPTION_TXGAIN:
05308 case AST_OPTION_RXGAIN:
05309
05310 errno = ENOSYS;
05311 return -1;
05312 case AST_OPTION_OPRMODE:
05313 errno = EINVAL;
05314 return -1;
05315 case AST_OPTION_SECURE_SIGNALING:
05316 case AST_OPTION_SECURE_MEDIA:
05317 {
05318 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
05319 ast_mutex_lock(&iaxsl[callno]);
05320 if ((*(int *) data)) {
05321 ast_set_flag64(iaxs[callno], IAX_FORCE_ENCRYPT);
05322 } else {
05323 ast_clear_flag64(iaxs[callno], IAX_FORCE_ENCRYPT);
05324 }
05325 ast_mutex_unlock(&iaxsl[callno]);
05326 return 0;
05327 }
05328
05329
05330
05331
05332 case AST_OPTION_TONE_VERIFY:
05333 case AST_OPTION_TDD:
05334 case AST_OPTION_RELAXDTMF:
05335 case AST_OPTION_AUDIO_MODE:
05336 case AST_OPTION_DIGIT_DETECT:
05337 case AST_OPTION_FAX_DETECT:
05338 {
05339 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
05340 struct chan_iax2_pvt *pvt;
05341
05342 ast_mutex_lock(&iaxsl[callno]);
05343 pvt = iaxs[callno];
05344
05345 if (wait_for_peercallno(pvt)) {
05346 ast_mutex_unlock(&iaxsl[callno]);
05347 return -1;
05348 }
05349
05350 ast_mutex_unlock(&iaxsl[callno]);
05351
05352 if (!(h = ast_malloc(datalen + sizeof(*h)))) {
05353 return -1;
05354 }
05355
05356 h->flag = AST_OPTION_FLAG_REQUEST;
05357 h->option = htons(option);
05358 memcpy(h->data, data, datalen);
05359 res = send_command_locked(PTR_TO_CALLNO(c->tech_pvt), AST_FRAME_CONTROL,
05360 AST_CONTROL_OPTION, 0, (unsigned char *) h,
05361 datalen + sizeof(*h), -1);
05362 ast_free(h);
05363 return res;
05364 }
05365 default:
05366 return -1;
05367 }
05368
05369
05370 return -1;
05371 }
05372
05373 static int iax2_queryoption(struct ast_channel *c, int option, void *data, int *datalen)
05374 {
05375 switch (option) {
05376 case AST_OPTION_SECURE_SIGNALING:
05377 case AST_OPTION_SECURE_MEDIA:
05378 {
05379 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
05380 ast_mutex_lock(&iaxsl[callno]);
05381 *((int *) data) = ast_test_flag64(iaxs[callno], IAX_FORCE_ENCRYPT) ? 1 : 0;
05382 ast_mutex_unlock(&iaxsl[callno]);
05383 return 0;
05384 }
05385 default:
05386 return -1;
05387 }
05388 }
05389
05390 static struct ast_frame *iax2_read(struct ast_channel *c)
05391 {
05392 ast_debug(1, "I should never be called!\n");
05393 return &ast_null_frame;
05394 }
05395
05396 static int iax2_key_rotate(const void *vpvt)
05397 {
05398 int res = 0;
05399 struct chan_iax2_pvt *pvt = (void *) vpvt;
05400 struct MD5Context md5;
05401 char key[17] = "";
05402 struct iax_ie_data ied = {
05403 .pos = 0,
05404 };
05405
05406 ast_mutex_lock(&iaxsl[pvt->callno]);
05407 pvt->keyrotateid =
05408 ast_sched_thread_add(sched, 120000 + (ast_random() % 180001), iax2_key_rotate, vpvt);
05409
05410 snprintf(key, sizeof(key), "%lX", ast_random());
05411
05412 MD5Init(&md5);
05413 MD5Update(&md5, (unsigned char *) key, strlen(key));
05414 MD5Final((unsigned char *) key, &md5);
05415
05416 IAX_DEBUGDIGEST("Sending", key);
05417
05418 iax_ie_append_raw(&ied, IAX_IE_CHALLENGE, key, 16);
05419
05420 res = send_command(pvt, AST_FRAME_IAX, IAX_COMMAND_RTKEY, 0, ied.buf, ied.pos, -1);
05421
05422 build_ecx_key((unsigned char *) key, pvt);
05423
05424 ast_mutex_unlock(&iaxsl[pvt->callno]);
05425
05426 return res;
05427 }
05428
05429 static int iax2_start_transfer(unsigned short callno0, unsigned short callno1, int mediaonly)
05430 {
05431 int res;
05432 struct iax_ie_data ied0;
05433 struct iax_ie_data ied1;
05434 unsigned int transferid = (unsigned int)ast_random();
05435
05436 if (IAX_CALLENCRYPTED(iaxs[callno0]) || IAX_CALLENCRYPTED(iaxs[callno1])) {
05437 ast_debug(1, "transfers are not supported for encrypted calls at this time\n");
05438 ast_set_flag64(iaxs[callno0], IAX_NOTRANSFER);
05439 ast_set_flag64(iaxs[callno1], IAX_NOTRANSFER);
05440 return 0;
05441 }
05442
05443 memset(&ied0, 0, sizeof(ied0));
05444 iax_ie_append_addr(&ied0, IAX_IE_APPARENT_ADDR, &iaxs[callno1]->addr);
05445 iax_ie_append_short(&ied0, IAX_IE_CALLNO, iaxs[callno1]->peercallno);
05446 iax_ie_append_int(&ied0, IAX_IE_TRANSFERID, transferid);
05447
05448 memset(&ied1, 0, sizeof(ied1));
05449 iax_ie_append_addr(&ied1, IAX_IE_APPARENT_ADDR, &iaxs[callno0]->addr);
05450 iax_ie_append_short(&ied1, IAX_IE_CALLNO, iaxs[callno0]->peercallno);
05451 iax_ie_append_int(&ied1, IAX_IE_TRANSFERID, transferid);
05452
05453 res = send_command(iaxs[callno0], AST_FRAME_IAX, IAX_COMMAND_TXREQ, 0, ied0.buf, ied0.pos, -1);
05454 if (res)
05455 return -1;
05456 res = send_command(iaxs[callno1], AST_FRAME_IAX, IAX_COMMAND_TXREQ, 0, ied1.buf, ied1.pos, -1);
05457 if (res)
05458 return -1;
05459 iaxs[callno0]->transferring = mediaonly ? TRANSFER_MBEGIN : TRANSFER_BEGIN;
05460 iaxs[callno1]->transferring = mediaonly ? TRANSFER_MBEGIN : TRANSFER_BEGIN;
05461 return 0;
05462 }
05463
05464 static void lock_both(unsigned short callno0, unsigned short callno1)
05465 {
05466 ast_mutex_lock(&iaxsl[callno0]);
05467 while (ast_mutex_trylock(&iaxsl[callno1])) {
05468 DEADLOCK_AVOIDANCE(&iaxsl[callno0]);
05469 }
05470 }
05471
05472 static void unlock_both(unsigned short callno0, unsigned short callno1)
05473 {
05474 ast_mutex_unlock(&iaxsl[callno1]);
05475 ast_mutex_unlock(&iaxsl[callno0]);
05476 }
05477
05478 static enum ast_bridge_result iax2_bridge(struct ast_channel *c0, struct ast_channel *c1, int flags, struct ast_frame **fo, struct ast_channel **rc, int timeoutms)
05479 {
05480 struct ast_channel *cs[3];
05481 struct ast_channel *who, *other;
05482 int to = -1;
05483 int res = -1;
05484 int transferstarted=0;
05485 struct ast_frame *f;
05486 unsigned short callno0 = PTR_TO_CALLNO(c0->tech_pvt);
05487 unsigned short callno1 = PTR_TO_CALLNO(c1->tech_pvt);
05488 struct timeval waittimer = {0, 0};
05489
05490
05491 if (timeoutms > 0) {
05492 return AST_BRIDGE_FAILED;
05493 }
05494
05495 timeoutms = -1;
05496
05497 lock_both(callno0, callno1);
05498 if (!iaxs[callno0] || !iaxs[callno1]) {
05499 unlock_both(callno0, callno1);
05500 return AST_BRIDGE_FAILED;
05501 }
05502
05503 if (!(flags & (AST_BRIDGE_DTMF_CHANNEL_0 | AST_BRIDGE_DTMF_CHANNEL_1))) {
05504 iaxs[callno0]->bridgecallno = callno1;
05505 iaxs[callno1]->bridgecallno = callno0;
05506 }
05507 unlock_both(callno0, callno1);
05508
05509
05510 cs[0] = c0;
05511 cs[1] = c1;
05512 for (;;) {
05513
05514 if ((c0->tech != &iax2_tech) || (c1->tech != &iax2_tech)) {
05515 ast_verb(3, "Can't masquerade, we're different...\n");
05516
05517 if (c0->tech == &iax2_tech) {
05518 ast_mutex_lock(&iaxsl[callno0]);
05519 iaxs[callno0]->bridgecallno = 0;
05520 ast_mutex_unlock(&iaxsl[callno0]);
05521 }
05522 if (c1->tech == &iax2_tech) {
05523 ast_mutex_lock(&iaxsl[callno1]);
05524 iaxs[callno1]->bridgecallno = 0;
05525 ast_mutex_unlock(&iaxsl[callno1]);
05526 }
05527 return AST_BRIDGE_FAILED_NOWARN;
05528 }
05529 if (c0->nativeformats != c1->nativeformats) {
05530 char buf0[256];
05531 char buf1[256];
05532 ast_getformatname_multiple(buf0, sizeof(buf0), c0->nativeformats);
05533 ast_getformatname_multiple(buf1, sizeof(buf1), c1->nativeformats);
05534 ast_verb(3, "Operating with different codecs [%s] [%s] , can't native bridge...\n", buf0, buf1);
05535
05536 lock_both(callno0, callno1);
05537 if (iaxs[callno0])
05538 iaxs[callno0]->bridgecallno = 0;
05539 if (iaxs[callno1])
05540 iaxs[callno1]->bridgecallno = 0;
05541 unlock_both(callno0, callno1);
05542 return AST_BRIDGE_FAILED_NOWARN;
05543 }
05544
05545 if (!transferstarted && !ast_test_flag64(iaxs[callno0], IAX_NOTRANSFER) && !ast_test_flag64(iaxs[callno1], IAX_NOTRANSFER)) {
05546
05547 if (iax2_start_transfer(callno0, callno1, (flags & (AST_BRIDGE_DTMF_CHANNEL_0 | AST_BRIDGE_DTMF_CHANNEL_1)) ||
05548 ast_test_flag64(iaxs[callno0], IAX_TRANSFERMEDIA) | ast_test_flag64(iaxs[callno1], IAX_TRANSFERMEDIA)))
05549 ast_log(LOG_WARNING, "Unable to start the transfer\n");
05550 transferstarted = 1;
05551 }
05552 if ((iaxs[callno0]->transferring == TRANSFER_RELEASED) && (iaxs[callno1]->transferring == TRANSFER_RELEASED)) {
05553
05554 struct timeval now = ast_tvnow();
05555 if (ast_tvzero(waittimer)) {
05556 waittimer = now;
05557 } else if (now.tv_sec - waittimer.tv_sec > IAX_LINGER_TIMEOUT) {
05558 c0->_softhangup |= AST_SOFTHANGUP_DEV;
05559 c1->_softhangup |= AST_SOFTHANGUP_DEV;
05560 *fo = NULL;
05561 *rc = c0;
05562 res = AST_BRIDGE_COMPLETE;
05563 break;
05564 }
05565 }
05566 to = 1000;
05567 who = ast_waitfor_n(cs, 2, &to);
05568 if (timeoutms > -1) {
05569 timeoutms -= (1000 - to);
05570 if (timeoutms < 0)
05571 timeoutms = 0;
05572 }
05573 if (!who) {
05574 if (!timeoutms) {
05575 res = AST_BRIDGE_RETRY;
05576 break;
05577 }
05578 if (ast_check_hangup(c0) || ast_check_hangup(c1)) {
05579 res = AST_BRIDGE_FAILED;
05580 break;
05581 }
05582 continue;
05583 }
05584 f = ast_read(who);
05585 if (!f) {
05586 *fo = NULL;
05587 *rc = who;
05588 res = AST_BRIDGE_COMPLETE;
05589 break;
05590 }
05591 if ((f->frametype == AST_FRAME_CONTROL) && !(flags & AST_BRIDGE_IGNORE_SIGS) && (f->subclass.integer != AST_CONTROL_SRCUPDATE)) {
05592 *fo = f;
05593 *rc = who;
05594 res = AST_BRIDGE_COMPLETE;
05595 break;
05596 }
05597 other = (who == c0) ? c1 : c0;
05598 if ((f->frametype == AST_FRAME_VOICE) ||
05599 (f->frametype == AST_FRAME_TEXT) ||
05600 (f->frametype == AST_FRAME_VIDEO) ||
05601 (f->frametype == AST_FRAME_IMAGE) ||
05602 (f->frametype == AST_FRAME_DTMF) ||
05603 (f->frametype == AST_FRAME_CONTROL)) {
05604
05605
05606
05607 int monitored_source = (who == c0) ? AST_BRIDGE_DTMF_CHANNEL_0 : AST_BRIDGE_DTMF_CHANNEL_1;
05608 if (f->frametype == AST_FRAME_DTMF && (flags & monitored_source)) {
05609 *rc = who;
05610 *fo = f;
05611 res = AST_BRIDGE_COMPLETE;
05612
05613 break;
05614 }
05615
05616 ast_write(other, f);
05617 }
05618 ast_frfree(f);
05619
05620 cs[2] = cs[0];
05621 cs[0] = cs[1];
05622 cs[1] = cs[2];
05623 }
05624 lock_both(callno0, callno1);
05625 if(iaxs[callno0])
05626 iaxs[callno0]->bridgecallno = 0;
05627 if(iaxs[callno1])
05628 iaxs[callno1]->bridgecallno = 0;
05629 unlock_both(callno0, callno1);
05630 return res;
05631 }
05632
05633 static int iax2_answer(struct ast_channel *c)
05634 {
05635 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
05636 ast_debug(1, "Answering IAX2 call\n");
05637 ast_mutex_lock(&iaxsl[callno]);
05638 if (iaxs[callno])
05639 iax2_ami_channelupdate(iaxs[callno]);
05640 ast_mutex_unlock(&iaxsl[callno]);
05641 return send_command_locked(callno, AST_FRAME_CONTROL, AST_CONTROL_ANSWER, 0, NULL, 0, -1);
05642 }
05643
05644 static int iax2_indicate(struct ast_channel *c, int condition, const void *data, size_t datalen)
05645 {
05646 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
05647 struct chan_iax2_pvt *pvt;
05648 int res = 0;
05649
05650 if (iaxdebug)
05651 ast_debug(1, "Indicating condition %d\n", condition);
05652
05653 ast_mutex_lock(&iaxsl[callno]);
05654 pvt = iaxs[callno];
05655
05656 if (wait_for_peercallno(pvt)) {
05657 res = -1;
05658 goto done;
05659 }
05660
05661 switch (condition) {
05662 case AST_CONTROL_HOLD:
05663 if (strcasecmp(pvt->mohinterpret, "passthrough")) {
05664 ast_moh_start(c, data, pvt->mohinterpret);
05665 goto done;
05666 }
05667 break;
05668 case AST_CONTROL_UNHOLD:
05669 if (strcasecmp(pvt->mohinterpret, "passthrough")) {
05670 ast_moh_stop(c);
05671 goto done;
05672 }
05673 break;
05674 case AST_CONTROL_CONNECTED_LINE:
05675 if (!ast_test_flag64(pvt, IAX_SENDCONNECTEDLINE))
05676 goto done;
05677 break;
05678 }
05679
05680 res = send_command(pvt, AST_FRAME_CONTROL, condition, 0, data, datalen, -1);
05681
05682 done:
05683 ast_mutex_unlock(&iaxsl[callno]);
05684
05685 return res;
05686 }
05687
05688 static int iax2_transfer(struct ast_channel *c, const char *dest)
05689 {
05690 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
05691 struct iax_ie_data ied = { "", };
05692 char tmp[256], *context;
05693 enum ast_control_transfer message = AST_TRANSFER_SUCCESS;
05694 ast_copy_string(tmp, dest, sizeof(tmp));
05695 context = strchr(tmp, '@');
05696 if (context) {
05697 *context = '\0';
05698 context++;
05699 }
05700 iax_ie_append_str(&ied, IAX_IE_CALLED_NUMBER, tmp);
05701 if (context)
05702 iax_ie_append_str(&ied, IAX_IE_CALLED_CONTEXT, context);
05703 ast_debug(1, "Transferring '%s' to '%s'\n", c->name, dest);
05704 ast_queue_control_data(c, AST_CONTROL_TRANSFER, &message, sizeof(message));
05705 return send_command_locked(callno, AST_FRAME_IAX, IAX_COMMAND_TRANSFER, 0, ied.buf, ied.pos, -1);
05706 }
05707
05708 static int iax2_getpeertrunk(struct sockaddr_in sin)
05709 {
05710 struct iax2_peer *peer;
05711 int res = 0;
05712 struct ao2_iterator i;
05713
05714 i = ao2_iterator_init(peers, 0);
05715 while ((peer = ao2_iterator_next(&i))) {
05716 struct sockaddr_in peer_addr;
05717
05718 ast_sockaddr_to_sin(&peer->addr, &peer_addr);
05719
05720 if ((peer_addr.sin_addr.s_addr == sin.sin_addr.s_addr) &&
05721 (peer_addr.sin_port == sin.sin_port)) {
05722 res = ast_test_flag64(peer, IAX_TRUNK);
05723 peer_unref(peer);
05724 break;
05725 }
05726 peer_unref(peer);
05727 }
05728 ao2_iterator_destroy(&i);
05729
05730 return res;
05731 }
05732
05733
05734 static struct ast_channel *ast_iax2_new(int callno, int state, format_t capability, const char *linkedid)
05735 {
05736 struct ast_channel *tmp;
05737 struct chan_iax2_pvt *i;
05738 struct ast_variable *v = NULL;
05739
05740 if (!(i = iaxs[callno])) {
05741 ast_log(LOG_WARNING, "No IAX2 pvt found for callno '%d' !\n", callno);
05742 return NULL;
05743 }
05744
05745
05746 ast_mutex_unlock(&iaxsl[callno]);
05747 tmp = ast_channel_alloc(1, state, i->cid_num, i->cid_name, i->accountcode, i->exten, i->context, linkedid, i->amaflags, "IAX2/%s-%d", i->host, i->callno);
05748 ast_mutex_lock(&iaxsl[callno]);
05749 if (i != iaxs[callno]) {
05750 if (tmp) {
05751
05752 ast_mutex_unlock(&iaxsl[callno]);
05753 tmp = ast_channel_release(tmp);
05754 ast_mutex_lock(&iaxsl[callno]);
05755 }
05756 return NULL;
05757 }
05758 iax2_ami_channelupdate(i);
05759 if (!tmp)
05760 return NULL;
05761 tmp->tech = &iax2_tech;
05762
05763 tmp->nativeformats = capability;
05764 tmp->readformat = tmp->rawreadformat = ast_best_codec(capability);
05765 tmp->writeformat = tmp->rawwriteformat = ast_best_codec(capability);
05766 tmp->tech_pvt = CALLNO_TO_PTR(i->callno);
05767
05768 if (!ast_strlen_zero(i->parkinglot))
05769 ast_string_field_set(tmp, parkinglot, i->parkinglot);
05770
05771
05772 if (!ast_strlen_zero(i->ani)) {
05773 tmp->caller.ani.number.valid = 1;
05774 tmp->caller.ani.number.str = ast_strdup(i->ani);
05775 } else if (!ast_strlen_zero(i->cid_num)) {
05776 tmp->caller.ani.number.valid = 1;
05777 tmp->caller.ani.number.str = ast_strdup(i->cid_num);
05778 }
05779 tmp->dialed.number.str = ast_strdup(i->dnid);
05780 if (!ast_strlen_zero(i->rdnis)) {
05781 tmp->redirecting.from.number.valid = 1;
05782 tmp->redirecting.from.number.str = ast_strdup(i->rdnis);
05783 }
05784 tmp->caller.id.name.presentation = i->calling_pres;
05785 tmp->caller.id.number.presentation = i->calling_pres;
05786 tmp->caller.id.number.plan = i->calling_ton;
05787 tmp->dialed.transit_network_select = i->calling_tns;
05788 if (!ast_strlen_zero(i->language))
05789 ast_string_field_set(tmp, language, i->language);
05790 if (!ast_strlen_zero(i->accountcode))
05791 ast_string_field_set(tmp, accountcode, i->accountcode);
05792 if (i->amaflags)
05793 tmp->amaflags = i->amaflags;
05794 ast_copy_string(tmp->context, i->context, sizeof(tmp->context));
05795 ast_copy_string(tmp->exten, i->exten, sizeof(tmp->exten));
05796 if (i->adsi)
05797 tmp->adsicpe = i->peeradsicpe;
05798 else
05799 tmp->adsicpe = AST_ADSI_UNAVAILABLE;
05800 i->owner = tmp;
05801 i->capability = capability;
05802
05803
05804 if (i->vars) {
05805 for (v = i->vars ; v ; v = v->next)
05806 pbx_builtin_setvar_helper(tmp, v->name, v->value);
05807 }
05808 if (i->iaxvars) {
05809 struct ast_datastore *variablestore;
05810 struct ast_variable *var, *prev = NULL;
05811 AST_LIST_HEAD(, ast_var_t) *varlist;
05812 ast_debug(1, "Loading up the channel with IAXVARs\n");
05813 varlist = ast_calloc(1, sizeof(*varlist));
05814 variablestore = ast_datastore_alloc(&iax2_variable_datastore_info, NULL);
05815 if (variablestore && varlist) {
05816 variablestore->data = varlist;
05817 variablestore->inheritance = DATASTORE_INHERIT_FOREVER;
05818 AST_LIST_HEAD_INIT(varlist);
05819 for (var = i->iaxvars; var; var = var->next) {
05820 struct ast_var_t *newvar = ast_var_assign(var->name, var->value);
05821 if (prev)
05822 ast_free(prev);
05823 prev = var;
05824 if (!newvar) {
05825
05826 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
05827 } else {
05828 AST_LIST_INSERT_TAIL(varlist, newvar, entries);
05829 }
05830 }
05831 if (prev)
05832 ast_free(prev);
05833 i->iaxvars = NULL;
05834 ast_channel_datastore_add(i->owner, variablestore);
05835 } else {
05836 if (variablestore) {
05837 ast_datastore_free(variablestore);
05838 }
05839 if (varlist) {
05840 ast_free(varlist);
05841 }
05842 }
05843 }
05844
05845 if (state != AST_STATE_DOWN) {
05846 if (ast_pbx_start(tmp)) {
05847 ast_log(LOG_WARNING, "Unable to start PBX on %s\n", tmp->name);
05848 ast_hangup(tmp);
05849 i->owner = NULL;
05850 return NULL;
05851 }
05852 }
05853
05854 ast_module_ref(ast_module_info->self);
05855 return tmp;
05856 }
05857
05858 static unsigned int calc_txpeerstamp(struct iax2_trunk_peer *tpeer, int sampms, struct timeval *now)
05859 {
05860 unsigned long int mssincetx;
05861 long int ms, pred;
05862
05863 tpeer->trunkact = *now;
05864 mssincetx = ast_tvdiff_ms(*now, tpeer->lasttxtime);
05865 if (mssincetx > 5000 || ast_tvzero(tpeer->txtrunktime)) {
05866
05867 tpeer->txtrunktime = *now;
05868 tpeer->lastsent = 999999;
05869 }
05870
05871 tpeer->lasttxtime = *now;
05872
05873
05874 ms = ast_tvdiff_ms(*now, tpeer->txtrunktime);
05875
05876 pred = tpeer->lastsent + sampms;
05877 if (abs(ms - pred) < MAX_TIMESTAMP_SKEW)
05878 ms = pred;
05879
05880
05881 if (ms == tpeer->lastsent)
05882 ms = tpeer->lastsent + 1;
05883 tpeer->lastsent = ms;
05884 return ms;
05885 }
05886
05887 static unsigned int fix_peerts(struct timeval *rxtrunktime, int callno, unsigned int ts)
05888 {
05889 long ms;
05890 if (ast_tvzero(iaxs[callno]->rxcore)) {
05891
05892 iaxs[callno]->rxcore = ast_tvnow();
05893
05894 iaxs[callno]->rxcore.tv_usec -= iaxs[callno]->rxcore.tv_usec % 20000;
05895 }
05896
05897 ms = ast_tvdiff_ms(*rxtrunktime, iaxs[callno]->rxcore);
05898
05899 return ms + ts;
05900 }
05901
05902 static unsigned int calc_timestamp(struct chan_iax2_pvt *p, unsigned int ts, struct ast_frame *f)
05903 {
05904 int ms;
05905 int voice = 0;
05906 int genuine = 0;
05907 int adjust;
05908 int rate = ast_format_rate(f->subclass.codec) / 1000;
05909 struct timeval *delivery = NULL;
05910
05911
05912
05913
05914
05915
05916
05917
05918 if (f->frametype == AST_FRAME_VOICE) {
05919 voice = 1;
05920 delivery = &f->delivery;
05921 } else if (f->frametype == AST_FRAME_IAX) {
05922 genuine = 1;
05923 } else if (f->frametype == AST_FRAME_CNG) {
05924 p->notsilenttx = 0;
05925 }
05926
05927 if (ast_tvzero(p->offset)) {
05928 p->offset = ast_tvnow();
05929
05930 p->offset.tv_usec -= p->offset.tv_usec % 20000;
05931 }
05932
05933 if (ts)
05934 return ts;
05935
05936 if (delivery && !ast_tvzero(*delivery)) {
05937 ms = ast_tvdiff_ms(*delivery, p->offset);
05938 if (ms < 0) {
05939 ms = 0;
05940 }
05941 if (iaxdebug)
05942 ast_debug(3, "calc_timestamp: call %d/%d: Timestamp slaved to delivery time\n", p->callno, iaxs[p->callno]->peercallno);
05943 } else {
05944 ms = ast_tvdiff_ms(ast_tvnow(), p->offset);
05945 if (ms < 0)
05946 ms = 0;
05947 if (voice) {
05948
05949 if (p->notsilenttx && abs(ms - p->nextpred) <= MAX_TIMESTAMP_SKEW) {
05950
05951
05952
05953
05954
05955
05956
05957
05958
05959
05960
05961
05962
05963
05964
05965
05966
05967
05968 adjust = (ms - p->nextpred);
05969 if (adjust < 0)
05970 p->offset = ast_tvsub(p->offset, ast_samp2tv(abs(adjust), 10000));
05971 else if (adjust > 0)
05972 p->offset = ast_tvadd(p->offset, ast_samp2tv(adjust, 10000));
05973
05974 if (!p->nextpred) {
05975 p->nextpred = ms;
05976 if (p->nextpred <= p->lastsent)
05977 p->nextpred = p->lastsent + 3;
05978 }
05979 ms = p->nextpred;
05980 } else {
05981
05982
05983
05984
05985
05986
05987
05988
05989
05990 if (iaxdebug && abs(ms - p->nextpred) > MAX_TIMESTAMP_SKEW )
05991 ast_debug(1, "predicted timestamp skew (%u) > max (%u), using real ts instead.\n",
05992 abs(ms - p->nextpred), MAX_TIMESTAMP_SKEW);
05993
05994 if (f->samples >= rate)
05995 {
05996 int diff = ms % (f->samples / rate);
05997 if (diff)
05998 ms += f->samples/rate - diff;
05999 }
06000
06001 p->nextpred = ms;
06002 p->notsilenttx = 1;
06003 }
06004 } else if ( f->frametype == AST_FRAME_VIDEO ) {
06005
06006
06007
06008
06009
06010
06011
06012
06013 if ( (unsigned int)ms < p->lastsent )
06014 ms = p->lastsent;
06015 } else {
06016
06017
06018 if (genuine) {
06019
06020 if (ms <= p->lastsent)
06021 ms = p->lastsent + 3;
06022 } else if (abs(ms - p->lastsent) <= MAX_TIMESTAMP_SKEW) {
06023
06024 ms = p->lastsent + 3;
06025 }
06026 }
06027 }
06028 p->lastsent = ms;
06029 if (voice)
06030 p->nextpred = p->nextpred + f->samples / rate;
06031 return ms;
06032 }
06033
06034 static unsigned int calc_rxstamp(struct chan_iax2_pvt *p, unsigned int offset)
06035 {
06036
06037
06038 int ms;
06039 #ifdef IAXTESTS
06040 int jit;
06041 #endif
06042
06043 if (ast_tvzero(p->rxcore)) {
06044 p->rxcore = ast_tvnow();
06045 if (iaxdebug)
06046 ast_debug(1, "calc_rxstamp: call=%d: rxcore set to %d.%6.6d - %dms\n",
06047 p->callno, (int)(p->rxcore.tv_sec), (int)(p->rxcore.tv_usec), offset);
06048 p->rxcore = ast_tvsub(p->rxcore, ast_samp2tv(offset, 1000));
06049 #if 1
06050 if (iaxdebug)
06051 ast_debug(1, "calc_rxstamp: call=%d: works out as %d.%6.6d\n",
06052 p->callno, (int)(p->rxcore.tv_sec),(int)( p->rxcore.tv_usec));
06053 #endif
06054 }
06055
06056 ms = ast_tvdiff_ms(ast_tvnow(), p->rxcore);
06057 #ifdef IAXTESTS
06058 if (test_jit) {
06059 if (!test_jitpct || ((100.0 * ast_random() / (RAND_MAX + 1.0)) < test_jitpct)) {
06060 jit = (int)((float)test_jit * ast_random() / (RAND_MAX + 1.0));
06061 if ((int)(2.0 * ast_random() / (RAND_MAX + 1.0)))
06062 jit = -jit;
06063 ms += jit;
06064 }
06065 }
06066 if (test_late) {
06067 ms += test_late;
06068 test_late = 0;
06069 }
06070 #endif
06071 return ms;
06072 }
06073
06074 static struct iax2_trunk_peer *find_tpeer(struct sockaddr_in *sin, int fd)
06075 {
06076 struct iax2_trunk_peer *tpeer = NULL;
06077
06078
06079 AST_LIST_LOCK(&tpeers);
06080
06081 AST_LIST_TRAVERSE(&tpeers, tpeer, list) {
06082 if (!inaddrcmp(&tpeer->addr, sin)) {
06083 ast_mutex_lock(&tpeer->lock);
06084 break;
06085 }
06086 }
06087
06088 if (!tpeer) {
06089 if ((tpeer = ast_calloc(1, sizeof(*tpeer)))) {
06090 ast_mutex_init(&tpeer->lock);
06091 tpeer->lastsent = 9999;
06092 memcpy(&tpeer->addr, sin, sizeof(tpeer->addr));
06093 tpeer->trunkact = ast_tvnow();
06094 ast_mutex_lock(&tpeer->lock);
06095 tpeer->sockfd = fd;
06096 #ifdef SO_NO_CHECK
06097 setsockopt(tpeer->sockfd, SOL_SOCKET, SO_NO_CHECK, &nochecksums, sizeof(nochecksums));
06098 #endif
06099 ast_debug(1, "Created trunk peer for '%s:%d'\n", ast_inet_ntoa(tpeer->addr.sin_addr), ntohs(tpeer->addr.sin_port));
06100 AST_LIST_INSERT_TAIL(&tpeers, tpeer, list);
06101 }
06102 }
06103
06104 AST_LIST_UNLOCK(&tpeers);
06105
06106 return tpeer;
06107 }
06108
06109 static int iax2_trunk_queue(struct chan_iax2_pvt *pvt, struct iax_frame *fr)
06110 {
06111 struct ast_frame *f;
06112 struct iax2_trunk_peer *tpeer;
06113 void *tmp, *ptr;
06114 struct timeval now;
06115 struct ast_iax2_meta_trunk_entry *met;
06116 struct ast_iax2_meta_trunk_mini *mtm;
06117
06118 f = &fr->af;
06119 tpeer = find_tpeer(&pvt->addr, pvt->sockfd);
06120 if (tpeer) {
06121 if (tpeer->trunkdatalen + f->datalen + 4 >= tpeer->trunkdataalloc) {
06122
06123 if (tpeer->trunkdataalloc < trunkmaxsize) {
06124 if (!(tmp = ast_realloc(tpeer->trunkdata, tpeer->trunkdataalloc + DEFAULT_TRUNKDATA + IAX2_TRUNK_PREFACE))) {
06125 ast_mutex_unlock(&tpeer->lock);
06126 return -1;
06127 }
06128
06129 tpeer->trunkdataalloc += DEFAULT_TRUNKDATA;
06130 tpeer->trunkdata = tmp;
06131 ast_debug(1, "Expanded trunk '%s:%d' to %d bytes\n", ast_inet_ntoa(tpeer->addr.sin_addr), ntohs(tpeer->addr.sin_port), tpeer->trunkdataalloc);
06132 } else {
06133 ast_log(LOG_WARNING, "Maximum trunk data space exceeded to %s:%d\n", ast_inet_ntoa(tpeer->addr.sin_addr), ntohs(tpeer->addr.sin_port));
06134 ast_mutex_unlock(&tpeer->lock);
06135 return -1;
06136 }
06137 }
06138
06139
06140 ptr = tpeer->trunkdata + IAX2_TRUNK_PREFACE + tpeer->trunkdatalen;
06141 if (ast_test_flag64(&globalflags, IAX_TRUNKTIMESTAMPS)) {
06142 mtm = (struct ast_iax2_meta_trunk_mini *)ptr;
06143 mtm->len = htons(f->datalen);
06144 mtm->mini.callno = htons(pvt->callno);
06145 mtm->mini.ts = htons(0xffff & fr->ts);
06146 ptr += sizeof(struct ast_iax2_meta_trunk_mini);
06147 tpeer->trunkdatalen += sizeof(struct ast_iax2_meta_trunk_mini);
06148 } else {
06149 met = (struct ast_iax2_meta_trunk_entry *)ptr;
06150
06151 met->callno = htons(pvt->callno);
06152 met->len = htons(f->datalen);
06153
06154 ptr += sizeof(struct ast_iax2_meta_trunk_entry);
06155 tpeer->trunkdatalen += sizeof(struct ast_iax2_meta_trunk_entry);
06156 }
06157
06158 memcpy(ptr, f->data.ptr, f->datalen);
06159 tpeer->trunkdatalen += f->datalen;
06160
06161 tpeer->calls++;
06162
06163
06164 if (tpeer->trunkdatalen + f->datalen + 4 > trunk_maxmtu)
06165 trunk_maxmtu = tpeer->trunkdatalen + f->datalen + 4 ;
06166
06167
06168 if (global_max_trunk_mtu > 0 && tpeer->trunkdatalen + f->datalen + 4 >= global_max_trunk_mtu) {
06169 now = ast_tvnow();
06170 send_trunk(tpeer, &now);
06171 trunk_untimed ++;
06172 }
06173
06174 ast_mutex_unlock(&tpeer->lock);
06175 }
06176 return 0;
06177 }
06178
06179
06180
06181 static void build_rand_pad(unsigned char *buf, ssize_t len)
06182 {
06183 long tmp;
06184 for (tmp = ast_random(); len > 0; tmp = ast_random()) {
06185 memcpy(buf, (unsigned char *) &tmp, (len > sizeof(tmp)) ? sizeof(tmp) : len);
06186 buf += sizeof(tmp);
06187 len -= sizeof(tmp);
06188 }
06189 }
06190
06191 static void build_encryption_keys(const unsigned char *digest, struct chan_iax2_pvt *pvt)
06192 {
06193 build_ecx_key(digest, pvt);
06194 ast_aes_set_decrypt_key(digest, &pvt->dcx);
06195 }
06196
06197 static void build_ecx_key(const unsigned char *digest, struct chan_iax2_pvt *pvt)
06198 {
06199
06200
06201
06202 build_rand_pad(pvt->semirand, sizeof(pvt->semirand));
06203 ast_aes_set_encrypt_key(digest, &pvt->ecx);
06204 ast_aes_set_decrypt_key(digest, &pvt->mydcx);
06205 }
06206
06207 static void memcpy_decrypt(unsigned char *dst, const unsigned char *src, int len, ast_aes_decrypt_key *dcx)
06208 {
06209 #if 0
06210
06211 int x;
06212 if (len % 16)
06213 ast_log(LOG_WARNING, "len should be multiple of 16, not %d!\n", len);
06214 for (x=0;x<len;x++)
06215 dst[x] = src[x] ^ 0xff;
06216 #else
06217 unsigned char lastblock[16] = { 0 };
06218 int x;
06219 while(len > 0) {
06220 ast_aes_decrypt(src, dst, dcx);
06221 for (x=0;x<16;x++)
06222 dst[x] ^= lastblock[x];
06223 memcpy(lastblock, src, sizeof(lastblock));
06224 dst += 16;
06225 src += 16;
06226 len -= 16;
06227 }
06228 #endif
06229 }
06230
06231 static void memcpy_encrypt(unsigned char *dst, const unsigned char *src, int len, ast_aes_encrypt_key *ecx)
06232 {
06233 #if 0
06234
06235 int x;
06236 if (len % 16)
06237 ast_log(LOG_WARNING, "len should be multiple of 16, not %d!\n", len);
06238 for (x=0;x<len;x++)
06239 dst[x] = src[x] ^ 0xff;
06240 #else
06241 unsigned char curblock[16] = { 0 };
06242 int x;
06243 while(len > 0) {
06244 for (x=0;x<16;x++)
06245 curblock[x] ^= src[x];
06246 ast_aes_encrypt(curblock, dst, ecx);
06247 memcpy(curblock, dst, sizeof(curblock));
06248 dst += 16;
06249 src += 16;
06250 len -= 16;
06251 }
06252 #endif
06253 }
06254
06255 static int decode_frame(ast_aes_decrypt_key *dcx, struct ast_iax2_full_hdr *fh, struct ast_frame *f, int *datalen)
06256 {
06257 int padding;
06258 unsigned char *workspace;
06259
06260 workspace = alloca(*datalen);
06261 memset(f, 0, sizeof(*f));
06262 if (ntohs(fh->scallno) & IAX_FLAG_FULL) {
06263 struct ast_iax2_full_enc_hdr *efh = (struct ast_iax2_full_enc_hdr *)fh;
06264 if (*datalen < 16 + sizeof(struct ast_iax2_full_hdr))
06265 return -1;
06266
06267 memcpy_decrypt(workspace, efh->encdata, *datalen - sizeof(struct ast_iax2_full_enc_hdr), dcx);
06268
06269 padding = 16 + (workspace[15] & 0x0f);
06270 if (iaxdebug)
06271 ast_debug(1, "Decoding full frame with length %d (padding = %d) (15=%02x)\n", *datalen, padding, workspace[15]);
06272 if (*datalen < padding + sizeof(struct ast_iax2_full_hdr))
06273 return -1;
06274
06275 *datalen -= padding;
06276 memcpy(efh->encdata, workspace + padding, *datalen - sizeof(struct ast_iax2_full_enc_hdr));
06277 f->frametype = fh->type;
06278 if (f->frametype == AST_FRAME_VIDEO) {
06279 f->subclass.codec = uncompress_subclass(fh->csub & ~0x40) | ((fh->csub >> 6) & 0x1);
06280 } else if (f->frametype == AST_FRAME_VOICE) {
06281 f->subclass.codec = uncompress_subclass(fh->csub);
06282 } else {
06283 f->subclass.integer = uncompress_subclass(fh->csub);
06284 }
06285 } else {
06286 struct ast_iax2_mini_enc_hdr *efh = (struct ast_iax2_mini_enc_hdr *)fh;
06287 if (iaxdebug)
06288 ast_debug(1, "Decoding mini with length %d\n", *datalen);
06289 if (*datalen < 16 + sizeof(struct ast_iax2_mini_hdr))
06290 return -1;
06291
06292 memcpy_decrypt(workspace, efh->encdata, *datalen - sizeof(struct ast_iax2_mini_enc_hdr), dcx);
06293 padding = 16 + (workspace[15] & 0x0f);
06294 if (*datalen < padding + sizeof(struct ast_iax2_mini_hdr))
06295 return -1;
06296 *datalen -= padding;
06297 memcpy(efh->encdata, workspace + padding, *datalen - sizeof(struct ast_iax2_mini_enc_hdr));
06298 }
06299 return 0;
06300 }
06301
06302 static int encrypt_frame(ast_aes_encrypt_key *ecx, struct ast_iax2_full_hdr *fh, unsigned char *poo, int *datalen)
06303 {
06304 int padding;
06305 unsigned char *workspace;
06306 workspace = alloca(*datalen + 32);
06307 if (!workspace)
06308 return -1;
06309 if (ntohs(fh->scallno) & IAX_FLAG_FULL) {
06310 struct ast_iax2_full_enc_hdr *efh = (struct ast_iax2_full_enc_hdr *)fh;
06311 if (iaxdebug)
06312 ast_debug(1, "Encoding full frame %d/%d with length %d\n", fh->type, fh->csub, *datalen);
06313 padding = 16 - ((*datalen - sizeof(struct ast_iax2_full_enc_hdr)) % 16);
06314 padding = 16 + (padding & 0xf);
06315 memcpy(workspace, poo, padding);
06316 memcpy(workspace + padding, efh->encdata, *datalen - sizeof(struct ast_iax2_full_enc_hdr));
06317 workspace[15] &= 0xf0;
06318 workspace[15] |= (padding & 0xf);
06319 if (iaxdebug)
06320 ast_debug(1, "Encoding full frame %d/%d with length %d + %d padding (15=%02x)\n", fh->type, fh->csub, *datalen, padding, workspace[15]);
06321 *datalen += padding;
06322 memcpy_encrypt(efh->encdata, workspace, *datalen - sizeof(struct ast_iax2_full_enc_hdr), ecx);
06323 if (*datalen >= 32 + sizeof(struct ast_iax2_full_enc_hdr))
06324 memcpy(poo, workspace + *datalen - 32, 32);
06325 } else {
06326 struct ast_iax2_mini_enc_hdr *efh = (struct ast_iax2_mini_enc_hdr *)fh;
06327 if (iaxdebug)
06328 ast_debug(1, "Encoding mini frame with length %d\n", *datalen);
06329 padding = 16 - ((*datalen - sizeof(struct ast_iax2_mini_enc_hdr)) % 16);
06330 padding = 16 + (padding & 0xf);
06331 memcpy(workspace, poo, padding);
06332 memcpy(workspace + padding, efh->encdata, *datalen - sizeof(struct ast_iax2_mini_enc_hdr));
06333 workspace[15] &= 0xf0;
06334 workspace[15] |= (padding & 0x0f);
06335 *datalen += padding;
06336 memcpy_encrypt(efh->encdata, workspace, *datalen - sizeof(struct ast_iax2_mini_enc_hdr), ecx);
06337 if (*datalen >= 32 + sizeof(struct ast_iax2_mini_enc_hdr))
06338 memcpy(poo, workspace + *datalen - 32, 32);
06339 }
06340 return 0;
06341 }
06342
06343 static int decrypt_frame(int callno, struct ast_iax2_full_hdr *fh, struct ast_frame *f, int *datalen)
06344 {
06345 int res=-1;
06346 if (!ast_test_flag64(iaxs[callno], IAX_KEYPOPULATED)) {
06347
06348 struct MD5Context md5;
06349 unsigned char digest[16];
06350 char *tmppw, *stringp;
06351
06352 tmppw = ast_strdupa(iaxs[callno]->secret);
06353 stringp = tmppw;
06354 while ((tmppw = strsep(&stringp, ";"))) {
06355 MD5Init(&md5);
06356 MD5Update(&md5, (unsigned char *)iaxs[callno]->challenge, strlen(iaxs[callno]->challenge));
06357 MD5Update(&md5, (unsigned char *)tmppw, strlen(tmppw));
06358 MD5Final(digest, &md5);
06359 build_encryption_keys(digest, iaxs[callno]);
06360 res = decode_frame(&iaxs[callno]->dcx, fh, f, datalen);
06361 if (!res) {
06362 ast_set_flag64(iaxs[callno], IAX_KEYPOPULATED);
06363 break;
06364 }
06365 }
06366 } else
06367 res = decode_frame(&iaxs[callno]->dcx, fh, f, datalen);
06368 return res;
06369 }
06370
06371 static int iax2_send(struct chan_iax2_pvt *pvt, struct ast_frame *f, unsigned int ts, int seqno, int now, int transfer, int final)
06372 {
06373
06374
06375
06376 struct ast_iax2_full_hdr *fh;
06377 struct ast_iax2_mini_hdr *mh;
06378 struct ast_iax2_video_hdr *vh;
06379 struct {
06380 struct iax_frame fr2;
06381 unsigned char buffer[4096];
06382 } frb;
06383 struct iax_frame *fr;
06384 int res;
06385 int sendmini=0;
06386 unsigned int lastsent;
06387 unsigned int fts;
06388
06389 frb.fr2.afdatalen = sizeof(frb.buffer);
06390
06391 if (!pvt) {
06392 ast_log(LOG_WARNING, "No private structure for packet?\n");
06393 return -1;
06394 }
06395
06396 lastsent = pvt->lastsent;
06397
06398
06399 fts = calc_timestamp(pvt, ts, f);
06400
06401
06402
06403
06404 if(f->frametype == AST_FRAME_VOICE && f->datalen == 0)
06405 return 0;
06406 #if 0
06407 ast_log(LOG_NOTICE,
06408 "f->frametype %c= AST_FRAME_VOICE, %sencrypted, %srotation scheduled...\n",
06409 *("=!" + (f->frametype == AST_FRAME_VOICE)),
06410 IAX_CALLENCRYPTED(pvt) ? "" : "not ",
06411 pvt->keyrotateid != -1 ? "" : "no "
06412 );
06413 #endif
06414 if (pvt->keyrotateid == -1 && f->frametype == AST_FRAME_VOICE && IAX_CALLENCRYPTED(pvt)) {
06415 iax2_key_rotate(pvt);
06416 }
06417
06418 if ((ast_test_flag64(pvt, IAX_TRUNK) ||
06419 (((fts & 0xFFFF0000L) == (lastsent & 0xFFFF0000L)) ||
06420 ((fts & 0xFFFF0000L) == ((lastsent + 0x10000) & 0xFFFF0000L))))
06421 &&
06422 (f->frametype == AST_FRAME_VOICE)
06423 &&
06424 (f->subclass.codec == pvt->svoiceformat)
06425 ) {
06426
06427 now = 1;
06428
06429 sendmini = 1;
06430 }
06431 if ( f->frametype == AST_FRAME_VIDEO ) {
06432
06433
06434
06435
06436
06437 if (((fts & 0xFFFF8000L) == (pvt->lastvsent & 0xFFFF8000L)) &&
06438 ((f->subclass.codec & ~0x1LL) == pvt->svideoformat)
06439 ) {
06440 now = 1;
06441 sendmini = 1;
06442 } else {
06443 now = 0;
06444 sendmini = 0;
06445 }
06446 pvt->lastvsent = fts;
06447 }
06448 if (f->frametype == AST_FRAME_IAX) {
06449
06450 pvt->last_iax_message = f->subclass.integer | MARK_IAX_SUBCLASS_TX;
06451 if (!pvt->first_iax_message) {
06452 pvt->first_iax_message = pvt->last_iax_message;
06453 }
06454 }
06455
06456 if (now) {
06457 fr = &frb.fr2;
06458 } else
06459 fr = iax_frame_new(DIRECTION_OUTGRESS, ast_test_flag64(pvt, IAX_ENCRYPTED) ? f->datalen + 32 : f->datalen, (f->frametype == AST_FRAME_VOICE) || (f->frametype == AST_FRAME_VIDEO));
06460 if (!fr) {
06461 ast_log(LOG_WARNING, "Out of memory\n");
06462 return -1;
06463 }
06464
06465 iax_frame_wrap(fr, f);
06466
06467 fr->ts = fts;
06468 fr->callno = pvt->callno;
06469 fr->transfer = transfer;
06470 fr->final = final;
06471 fr->encmethods = 0;
06472 if (!sendmini) {
06473
06474 if (seqno > -1)
06475 fr->oseqno = seqno;
06476 else
06477 fr->oseqno = pvt->oseqno++;
06478 fr->iseqno = pvt->iseqno;
06479 fh = (struct ast_iax2_full_hdr *)(fr->af.data.ptr - sizeof(struct ast_iax2_full_hdr));
06480 fh->scallno = htons(fr->callno | IAX_FLAG_FULL);
06481 fh->ts = htonl(fr->ts);
06482 fh->oseqno = fr->oseqno;
06483 if (transfer) {
06484 fh->iseqno = 0;
06485 } else
06486 fh->iseqno = fr->iseqno;
06487
06488 if (!transfer)
06489 pvt->aseqno = fr->iseqno;
06490 fh->type = fr->af.frametype & 0xFF;
06491
06492 if (fr->af.frametype == AST_FRAME_VIDEO) {
06493 fh->csub = compress_subclass(fr->af.subclass.codec & ~0x1LL) | ((fr->af.subclass.codec & 0x1LL) << 6);
06494 } else if (fr->af.frametype == AST_FRAME_VOICE) {
06495 fh->csub = compress_subclass(fr->af.subclass.codec);
06496 } else {
06497 fh->csub = compress_subclass(fr->af.subclass.integer);
06498 }
06499
06500 if (transfer) {
06501 fr->dcallno = pvt->transfercallno;
06502 } else
06503 fr->dcallno = pvt->peercallno;
06504 fh->dcallno = htons(fr->dcallno);
06505 fr->datalen = fr->af.datalen + sizeof(struct ast_iax2_full_hdr);
06506 fr->data = fh;
06507 fr->retries = 0;
06508
06509 fr->retrytime = pvt->pingtime * 2;
06510 if (fr->retrytime < MIN_RETRY_TIME)
06511 fr->retrytime = MIN_RETRY_TIME;
06512 if (fr->retrytime > MAX_RETRY_TIME)
06513 fr->retrytime = MAX_RETRY_TIME;
06514
06515 if ((f->frametype == AST_FRAME_IAX) && (f->subclass.integer == IAX_COMMAND_ACK))
06516 fr->retries = -1;
06517 else if (f->frametype == AST_FRAME_VOICE)
06518 pvt->svoiceformat = f->subclass.codec;
06519 else if (f->frametype == AST_FRAME_VIDEO)
06520 pvt->svideoformat = f->subclass.codec & ~0x1LL;
06521 if (ast_test_flag64(pvt, IAX_ENCRYPTED)) {
06522 if (ast_test_flag64(pvt, IAX_KEYPOPULATED)) {
06523 if (fr->transfer)
06524 iax_outputframe(fr, NULL, 2, &pvt->transfer, fr->datalen - sizeof(struct ast_iax2_full_hdr));
06525 else
06526 iax_outputframe(fr, NULL, 2, &pvt->addr, fr->datalen - sizeof(struct ast_iax2_full_hdr));
06527 encrypt_frame(&pvt->ecx, fh, pvt->semirand, &fr->datalen);
06528 fr->encmethods = pvt->encmethods;
06529 fr->ecx = pvt->ecx;
06530 fr->mydcx = pvt->mydcx;
06531 memcpy(fr->semirand, pvt->semirand, sizeof(fr->semirand));
06532 } else
06533 ast_log(LOG_WARNING, "Supposed to send packet encrypted, but no key?\n");
06534 }
06535
06536 if (now) {
06537 res = send_packet(fr);
06538 } else
06539 res = iax2_transmit(fr);
06540 } else {
06541 if (ast_test_flag64(pvt, IAX_TRUNK)) {
06542 iax2_trunk_queue(pvt, fr);
06543 res = 0;
06544 } else if (fr->af.frametype == AST_FRAME_VIDEO) {
06545
06546 fr->oseqno = -1;
06547 fr->iseqno = -1;
06548 vh = (struct ast_iax2_video_hdr *)(fr->af.data.ptr - sizeof(struct ast_iax2_video_hdr));
06549 vh->zeros = 0;
06550 vh->callno = htons(0x8000 | fr->callno);
06551 vh->ts = htons((fr->ts & 0x7FFF) | (fr->af.subclass.codec & 0x1LL ? 0x8000 : 0));
06552 fr->datalen = fr->af.datalen + sizeof(struct ast_iax2_video_hdr);
06553 fr->data = vh;
06554 fr->retries = -1;
06555 res = send_packet(fr);
06556 } else {
06557
06558 fr->oseqno = -1;
06559 fr->iseqno = -1;
06560
06561 mh = (struct ast_iax2_mini_hdr *)(fr->af.data.ptr - sizeof(struct ast_iax2_mini_hdr));
06562 mh->callno = htons(fr->callno);
06563 mh->ts = htons(fr->ts & 0xFFFF);
06564 fr->datalen = fr->af.datalen + sizeof(struct ast_iax2_mini_hdr);
06565 fr->data = mh;
06566 fr->retries = -1;
06567 if (pvt->transferring == TRANSFER_MEDIAPASS)
06568 fr->transfer = 1;
06569 if (ast_test_flag64(pvt, IAX_ENCRYPTED)) {
06570 if (ast_test_flag64(pvt, IAX_KEYPOPULATED)) {
06571 encrypt_frame(&pvt->ecx, (struct ast_iax2_full_hdr *)mh, pvt->semirand, &fr->datalen);
06572 } else
06573 ast_log(LOG_WARNING, "Supposed to send packet encrypted, but no key?\n");
06574 }
06575 res = send_packet(fr);
06576 }
06577 }
06578 return res;
06579 }
06580
06581 static char *handle_cli_iax2_show_users(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
06582 {
06583 regex_t regexbuf;
06584 int havepattern = 0;
06585
06586 #define FORMAT "%-15.15s %-20.20s %-15.15s %-15.15s %-5.5s %-5.10s\n"
06587 #define FORMAT2 "%-15.15s %-20.20s %-15.15d %-15.15s %-5.5s %-5.10s\n"
06588
06589 struct iax2_user *user = NULL;
06590 char auth[90];
06591 char *pstr = "";
06592 struct ao2_iterator i;
06593
06594 switch (cmd) {
06595 case CLI_INIT:
06596 e->command = "iax2 show users [like]";
06597 e->usage =
06598 "Usage: iax2 show users [like <pattern>]\n"
06599 " Lists all known IAX2 users.\n"
06600 " Optional regular expression pattern is used to filter the user list.\n";
06601 return NULL;
06602 case CLI_GENERATE:
06603 return NULL;
06604 }
06605
06606 switch (a->argc) {
06607 case 5:
06608 if (!strcasecmp(a->argv[3], "like")) {
06609 if (regcomp(®exbuf, a->argv[4], REG_EXTENDED | REG_NOSUB))
06610 return CLI_SHOWUSAGE;
06611 havepattern = 1;
06612 } else
06613 return CLI_SHOWUSAGE;
06614 case 3:
06615 break;
06616 default:
06617 return CLI_SHOWUSAGE;
06618 }
06619
06620 ast_cli(a->fd, FORMAT, "Username", "Secret", "Authen", "Def.Context", "A/C","Codec Pref");
06621 i = ao2_iterator_init(users, 0);
06622 for (; (user = ao2_iterator_next(&i)); user_unref(user)) {
06623 if (havepattern && regexec(®exbuf, user->name, 0, NULL, 0))
06624 continue;
06625
06626 if (!ast_strlen_zero(user->secret)) {
06627 ast_copy_string(auth,user->secret, sizeof(auth));
06628 } else if (!ast_strlen_zero(user->inkeys)) {
06629 snprintf(auth, sizeof(auth), "Key: %-15.15s ", user->inkeys);
06630 } else
06631 ast_copy_string(auth, "-no secret-", sizeof(auth));
06632
06633 if(ast_test_flag64(user, IAX_CODEC_NOCAP))
06634 pstr = "REQ Only";
06635 else if(ast_test_flag64(user, IAX_CODEC_NOPREFS))
06636 pstr = "Disabled";
06637 else
06638 pstr = ast_test_flag64(user, IAX_CODEC_USER_FIRST) ? "Caller" : "Host";
06639
06640 ast_cli(a->fd, FORMAT2, user->name, auth, user->authmethods,
06641 user->contexts ? user->contexts->context : DEFAULT_CONTEXT,
06642 user->ha ? "Yes" : "No", pstr);
06643 }
06644 ao2_iterator_destroy(&i);
06645
06646 if (havepattern)
06647 regfree(®exbuf);
06648
06649 return CLI_SUCCESS;
06650 #undef FORMAT
06651 #undef FORMAT2
06652 }
06653
06654 static int __iax2_show_peers(int fd, int *total, struct mansession *s, const int argc, const char * const argv[])
06655 {
06656 regex_t regexbuf;
06657 int havepattern = 0;
06658 int total_peers = 0;
06659 int online_peers = 0;
06660 int offline_peers = 0;
06661 int unmonitored_peers = 0;
06662 struct ao2_iterator i;
06663
06664 #define FORMAT2 "%-15.15s %-15.15s %s %-15.15s %-8s %s %-10s\n"
06665 #define FORMAT "%-15.15s %-15.15s %s %-15.15s %-5d%s %s %-10s\n"
06666
06667 struct iax2_peer *peer = NULL;
06668 char name[256];
06669 struct ast_str *encmethods = ast_str_alloca(256);
06670 int registeredonly=0;
06671 char idtext[256] = "";
06672 switch (argc) {
06673 case 6:
06674 if (!strcasecmp(argv[3], "registered"))
06675 registeredonly = 1;
06676 else
06677 return RESULT_SHOWUSAGE;
06678 if (!strcasecmp(argv[4], "like")) {
06679 if (regcomp(®exbuf, argv[5], REG_EXTENDED | REG_NOSUB))
06680 return RESULT_SHOWUSAGE;
06681 havepattern = 1;
06682 } else
06683 return RESULT_SHOWUSAGE;
06684 break;
06685 case 5:
06686 if (!strcasecmp(argv[3], "like")) {
06687 if (regcomp(®exbuf, argv[4], REG_EXTENDED | REG_NOSUB))
06688 return RESULT_SHOWUSAGE;
06689 havepattern = 1;
06690 } else
06691 return RESULT_SHOWUSAGE;
06692 break;
06693 case 4:
06694 if (!strcasecmp(argv[3], "registered"))
06695 registeredonly = 1;
06696 else
06697 return RESULT_SHOWUSAGE;
06698 break;
06699 case 3:
06700 break;
06701 default:
06702 return RESULT_SHOWUSAGE;
06703 }
06704
06705
06706 if (!s)
06707 ast_cli(fd, FORMAT2, "Name/Username", "Host", " ", "Mask", "Port", " ", "Status");
06708
06709 i = ao2_iterator_init(peers, 0);
06710 for (; (peer = ao2_iterator_next(&i)); peer_unref(peer)) {
06711 char nm[20];
06712 char status[20];
06713 int retstatus;
06714 struct sockaddr_in peer_addr;
06715
06716 ast_sockaddr_to_sin(&peer->addr, &peer_addr);
06717
06718 if (registeredonly && !peer_addr.sin_addr.s_addr) {
06719 continue;
06720 }
06721 if (havepattern && regexec(®exbuf, peer->name, 0, NULL, 0)) {
06722 continue;
06723 }
06724
06725 if (!ast_strlen_zero(peer->username))
06726 snprintf(name, sizeof(name), "%s/%s", peer->name, peer->username);
06727 else
06728 ast_copy_string(name, peer->name, sizeof(name));
06729
06730 encmethods_to_str(peer->encmethods, encmethods);
06731 retstatus = peer_status(peer, status, sizeof(status));
06732 if (retstatus > 0)
06733 online_peers++;
06734 else if (!retstatus)
06735 offline_peers++;
06736 else
06737 unmonitored_peers++;
06738
06739 ast_copy_string(nm, ast_inet_ntoa(peer->mask), sizeof(nm));
06740
06741 if (s) {
06742 astman_append(s,
06743 "Event: PeerEntry\r\n%s"
06744 "Channeltype: IAX2\r\n"
06745 "ObjectName: %s\r\n"
06746 "ChanObjectType: peer\r\n"
06747 "IPaddress: %s\r\n"
06748 "IPport: %d\r\n"
06749 "Dynamic: %s\r\n"
06750 "Trunk: %s\r\n"
06751 "Encryption: %s\r\n"
06752 "Status: %s\r\n\r\n",
06753 idtext,
06754 name,
06755 ast_sockaddr_stringify_addr(&peer->addr),
06756 ast_sockaddr_port(&peer->addr),
06757 ast_test_flag64(peer, IAX_DYNAMIC) ? "yes" : "no",
06758 ast_test_flag64(peer, IAX_TRUNK) ? "yes" : "no",
06759 peer->encmethods ? ast_str_buffer(encmethods) : "no",
06760 status);
06761 } else {
06762 ast_cli(fd, FORMAT, name,
06763 ast_sockaddr_stringify_addr(&peer->addr),
06764 ast_test_flag64(peer, IAX_DYNAMIC) ? "(D)" : "(S)",
06765 nm,
06766 ast_sockaddr_port(&peer->addr),
06767 ast_test_flag64(peer, IAX_TRUNK) ? "(T)" : " ",
06768 peer->encmethods ? "(E)" : " ",
06769 status);
06770 }
06771 total_peers++;
06772 }
06773 ao2_iterator_destroy(&i);
06774
06775 if (!s)
06776 ast_cli(fd,"%d iax2 peers [%d online, %d offline, %d unmonitored]\n",
06777 total_peers, online_peers, offline_peers, unmonitored_peers);
06778
06779 if (havepattern)
06780 regfree(®exbuf);
06781
06782 if (total)
06783 *total = total_peers;
06784
06785 return RESULT_SUCCESS;
06786 #undef FORMAT
06787 #undef FORMAT2
06788 }
06789
06790 static char *handle_cli_iax2_show_threads(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
06791 {
06792 struct iax2_thread *thread = NULL;
06793 time_t t;
06794 int threadcount = 0, dynamiccount = 0;
06795 char type;
06796
06797 switch (cmd) {
06798 case CLI_INIT:
06799 e->command = "iax2 show threads";
06800 e->usage =
06801 "Usage: iax2 show threads\n"
06802 " Lists status of IAX helper threads\n";
06803 return NULL;
06804 case CLI_GENERATE:
06805 return NULL;
06806 }
06807 if (a->argc != 3)
06808 return CLI_SHOWUSAGE;
06809
06810 ast_cli(a->fd, "IAX2 Thread Information\n");
06811 time(&t);
06812 ast_cli(a->fd, "Idle Threads:\n");
06813 AST_LIST_LOCK(&idle_list);
06814 AST_LIST_TRAVERSE(&idle_list, thread, list) {
06815 #ifdef DEBUG_SCHED_MULTITHREAD
06816 ast_cli(a->fd, "Thread %d: state=%d, update=%d, actions=%d, func='%s'\n",
06817 thread->threadnum, thread->iostate, (int)(t - thread->checktime), thread->actions, thread->curfunc);
06818 #else
06819 ast_cli(a->fd, "Thread %d: state=%d, update=%d, actions=%d\n",
06820 thread->threadnum, thread->iostate, (int)(t - thread->checktime), thread->actions);
06821 #endif
06822 threadcount++;
06823 }
06824 AST_LIST_UNLOCK(&idle_list);
06825 ast_cli(a->fd, "Active Threads:\n");
06826 AST_LIST_LOCK(&active_list);
06827 AST_LIST_TRAVERSE(&active_list, thread, list) {
06828 if (thread->type == IAX_THREAD_TYPE_DYNAMIC)
06829 type = 'D';
06830 else
06831 type = 'P';
06832 #ifdef DEBUG_SCHED_MULTITHREAD
06833 ast_cli(a->fd, "Thread %c%d: state=%d, update=%d, actions=%d, func='%s'\n",
06834 type, thread->threadnum, thread->iostate, (int)(t - thread->checktime), thread->actions, thread->curfunc);
06835 #else
06836 ast_cli(a->fd, "Thread %c%d: state=%d, update=%d, actions=%d\n",
06837 type, thread->threadnum, thread->iostate, (int)(t - thread->checktime), thread->actions);
06838 #endif
06839 threadcount++;
06840 }
06841 AST_LIST_UNLOCK(&active_list);
06842 ast_cli(a->fd, "Dynamic Threads:\n");
06843 AST_LIST_LOCK(&dynamic_list);
06844 AST_LIST_TRAVERSE(&dynamic_list, thread, list) {
06845 #ifdef DEBUG_SCHED_MULTITHREAD
06846 ast_cli(a->fd, "Thread %d: state=%d, update=%d, actions=%d, func='%s'\n",
06847 thread->threadnum, thread->iostate, (int)(t - thread->checktime), thread->actions, thread->curfunc);
06848 #else
06849 ast_cli(a->fd, "Thread %d: state=%d, update=%d, actions=%d\n",
06850 thread->threadnum, thread->iostate, (int)(t - thread->checktime), thread->actions);
06851 #endif
06852 dynamiccount++;
06853 }
06854 AST_LIST_UNLOCK(&dynamic_list);
06855 ast_cli(a->fd, "%d of %d threads accounted for with %d dynamic threads\n", threadcount, iaxthreadcount, dynamiccount);
06856 return CLI_SUCCESS;
06857 }
06858
06859 static char *handle_cli_iax2_unregister(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
06860 {
06861 struct iax2_peer *p;
06862
06863 switch (cmd) {
06864 case CLI_INIT:
06865 e->command = "iax2 unregister";
06866 e->usage =
06867 "Usage: iax2 unregister <peername>\n"
06868 " Unregister (force expiration) an IAX2 peer from the registry.\n";
06869 return NULL;
06870 case CLI_GENERATE:
06871 return complete_iax2_unregister(a->line, a->word, a->pos, a->n);
06872 }
06873
06874 if (a->argc != 3)
06875 return CLI_SHOWUSAGE;
06876
06877 p = find_peer(a->argv[2], 1);
06878 if (p) {
06879 if (p->expire > 0) {
06880 struct iax2_peer tmp_peer = {
06881 .name = a->argv[2],
06882 };
06883 struct iax2_peer *peer;
06884
06885 peer = ao2_find(peers, &tmp_peer, OBJ_POINTER);
06886 if (peer) {
06887 expire_registry(peer_ref(peer));
06888 peer_unref(peer);
06889 ast_cli(a->fd, "Peer %s unregistered\n", a->argv[2]);
06890 } else {
06891 ast_cli(a->fd, "Peer %s not found\n", a->argv[2]);
06892 }
06893 } else {
06894 ast_cli(a->fd, "Peer %s not registered\n", a->argv[2]);
06895 }
06896 peer_unref(p);
06897 } else {
06898 ast_cli(a->fd, "Peer unknown: %s. Not unregistered\n", a->argv[2]);
06899 }
06900 return CLI_SUCCESS;
06901 }
06902
06903 static char *complete_iax2_unregister(const char *line, const char *word, int pos, int state)
06904 {
06905 int which = 0;
06906 struct iax2_peer *p = NULL;
06907 char *res = NULL;
06908 int wordlen = strlen(word);
06909
06910
06911 if (pos == 2) {
06912 struct ao2_iterator i = ao2_iterator_init(peers, 0);
06913 while ((p = ao2_iterator_next(&i))) {
06914 if (!strncasecmp(p->name, word, wordlen) &&
06915 ++which > state && p->expire > 0) {
06916 res = ast_strdup(p->name);
06917 peer_unref(p);
06918 break;
06919 }
06920 peer_unref(p);
06921 }
06922 ao2_iterator_destroy(&i);
06923 }
06924
06925 return res;
06926 }
06927
06928 static char *handle_cli_iax2_show_peers(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
06929 {
06930 switch (cmd) {
06931 case CLI_INIT:
06932 e->command = "iax2 show peers";
06933 e->usage =
06934 "Usage: iax2 show peers [registered] [like <pattern>]\n"
06935 " Lists all known IAX2 peers.\n"
06936 " Optional 'registered' argument lists only peers with known addresses.\n"
06937 " Optional regular expression pattern is used to filter the peer list.\n";
06938 return NULL;
06939 case CLI_GENERATE:
06940 return NULL;
06941 }
06942
06943 switch (__iax2_show_peers(a->fd, NULL, NULL, a->argc, a->argv)) {
06944 case RESULT_SHOWUSAGE:
06945 return CLI_SHOWUSAGE;
06946 case RESULT_FAILURE:
06947 return CLI_FAILURE;
06948 default:
06949 return CLI_SUCCESS;
06950 }
06951 }
06952
06953 static int manager_iax2_show_netstats(struct mansession *s, const struct message *m)
06954 {
06955 ast_cli_netstats(s, -1, 0);
06956 astman_append(s, "\r\n");
06957 return RESULT_SUCCESS;
06958 }
06959
06960 static char *handle_cli_iax2_show_firmware(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
06961 {
06962 struct iax_firmware *cur = NULL;
06963
06964 switch (cmd) {
06965 case CLI_INIT:
06966 e->command = "iax2 show firmware";
06967 e->usage =
06968 "Usage: iax2 show firmware\n"
06969 " Lists all known IAX firmware images.\n";
06970 return NULL;
06971 case CLI_GENERATE:
06972 return NULL;
06973 }
06974
06975 if (a->argc != 3 && a->argc != 4)
06976 return CLI_SHOWUSAGE;
06977
06978 ast_cli(a->fd, "%-15.15s %-15.15s %-15.15s\n", "Device", "Version", "Size");
06979 AST_LIST_LOCK(&firmwares);
06980 AST_LIST_TRAVERSE(&firmwares, cur, list) {
06981 if ((a->argc == 3) || (!strcasecmp(a->argv[3], (char *) cur->fwh->devname))) {
06982 ast_cli(a->fd, "%-15.15s %-15d %-15d\n", cur->fwh->devname,
06983 ntohs(cur->fwh->version), (int)ntohl(cur->fwh->datalen));
06984 }
06985 }
06986 AST_LIST_UNLOCK(&firmwares);
06987
06988 return CLI_SUCCESS;
06989 }
06990
06991
06992 static int manager_iax2_show_peers(struct mansession *s, const struct message *m)
06993 {
06994 static const char * const a[] = { "iax2", "show", "peers" };
06995 const char *id = astman_get_header(m,"ActionID");
06996 char idtext[256] = "";
06997 int total = 0;
06998
06999 if (!ast_strlen_zero(id))
07000 snprintf(idtext, sizeof(idtext), "ActionID: %s\r\n", id);
07001
07002 astman_send_listack(s, m, "Peer status list will follow", "start");
07003
07004 __iax2_show_peers(-1, &total, s, 3, a);
07005
07006 astman_append(s,
07007 "Event: PeerlistComplete\r\n"
07008 "EventList: Complete\r\n"
07009 "ListItems: %d\r\n"
07010 "%s"
07011 "\r\n", total, idtext);
07012 return 0;
07013 }
07014
07015
07016 static int manager_iax2_show_peer_list(struct mansession *s, const struct message *m)
07017 {
07018 struct iax2_peer *peer = NULL;
07019 int peer_count = 0;
07020 char nm[20];
07021 char status[20];
07022 const char *id = astman_get_header(m,"ActionID");
07023 char idtext[256] = "";
07024 struct ast_str *encmethods = ast_str_alloca(256);
07025 struct ao2_iterator i;
07026
07027 if (!ast_strlen_zero(id))
07028 snprintf(idtext, sizeof(idtext), "ActionID: %s\r\n", id);
07029
07030 astman_append(s, "Response: Success\r\n%sMessage: IAX Peer status list will follow\r\n\r\n", idtext);
07031
07032
07033 i = ao2_iterator_init(peers, 0);
07034 for (; (peer = ao2_iterator_next(&i)); peer_unref(peer)) {
07035 encmethods_to_str(peer->encmethods, encmethods);
07036 astman_append(s, "Event: PeerEntry\r\n%sChanneltype: IAX\r\n", idtext);
07037 if (!ast_strlen_zero(peer->username)) {
07038 astman_append(s, "ObjectName: %s\r\nObjectUsername: %s\r\n", peer->name, peer->username);
07039 } else {
07040 astman_append(s, "ObjectName: %s\r\n", peer->name);
07041 }
07042 astman_append(s, "ChanObjectType: peer\r\n");
07043 astman_append(s, "IPaddress: %s\r\n", ast_sockaddr_stringify_addr(&peer->addr));
07044 ast_copy_string(nm, ast_inet_ntoa(peer->mask), sizeof(nm));
07045 astman_append(s, "Mask: %s\r\n", nm);
07046 astman_append(s, "Port: %d\r\n", ast_sockaddr_port(&peer->addr));
07047 astman_append(s, "Dynamic: %s\r\n", ast_test_flag64(peer, IAX_DYNAMIC) ? "Yes" : "No");
07048 astman_append(s, "Trunk: %s\r\n", ast_test_flag64(peer, IAX_TRUNK) ? "Yes" : "No");
07049 astman_append(s, "Encryption: %s\r\n", peer->encmethods ? ast_str_buffer(encmethods) : "No");
07050 peer_status(peer, status, sizeof(status));
07051 astman_append(s, "Status: %s\r\n\r\n", status);
07052 peer_count++;
07053 }
07054 ao2_iterator_destroy(&i);
07055
07056 astman_append(s, "Event: PeerlistComplete\r\n%sListItems: %d\r\n\r\n", idtext, peer_count);
07057 return RESULT_SUCCESS;
07058 }
07059
07060
07061 static char *regstate2str(int regstate)
07062 {
07063 switch(regstate) {
07064 case REG_STATE_UNREGISTERED:
07065 return "Unregistered";
07066 case REG_STATE_REGSENT:
07067 return "Request Sent";
07068 case REG_STATE_AUTHSENT:
07069 return "Auth. Sent";
07070 case REG_STATE_REGISTERED:
07071 return "Registered";
07072 case REG_STATE_REJECTED:
07073 return "Rejected";
07074 case REG_STATE_TIMEOUT:
07075 return "Timeout";
07076 case REG_STATE_NOAUTH:
07077 return "No Authentication";
07078 default:
07079 return "Unknown";
07080 }
07081 }
07082
07083 static char *handle_cli_iax2_show_registry(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
07084 {
07085 #define FORMAT2 "%-20.20s %-6.6s %-10.10s %-20.20s %8.8s %s\n"
07086 #define FORMAT "%-20.20s %-6.6s %-10.10s %-20.20s %8d %s\n"
07087 struct iax2_registry *reg = NULL;
07088 char host[80];
07089 char perceived[80];
07090 int counter = 0;
07091
07092 switch (cmd) {
07093 case CLI_INIT:
07094 e->command = "iax2 show registry";
07095 e->usage =
07096 "Usage: iax2 show registry\n"
07097 " Lists all registration requests and status.\n";
07098 return NULL;
07099 case CLI_GENERATE:
07100 return NULL;
07101 }
07102 if (a->argc != 3)
07103 return CLI_SHOWUSAGE;
07104 ast_cli(a->fd, FORMAT2, "Host", "dnsmgr", "Username", "Perceived", "Refresh", "State");
07105 AST_LIST_LOCK(®istrations);
07106 AST_LIST_TRAVERSE(®istrations, reg, entry) {
07107 snprintf(host, sizeof(host), "%s", ast_sockaddr_stringify(®->addr));
07108 if (reg->us.sin_addr.s_addr)
07109 snprintf(perceived, sizeof(perceived), "%s:%d", ast_inet_ntoa(reg->us.sin_addr), ntohs(reg->us.sin_port));
07110 else
07111 ast_copy_string(perceived, "<Unregistered>", sizeof(perceived));
07112 ast_cli(a->fd, FORMAT, host,
07113 (reg->dnsmgr) ? "Y" : "N",
07114 reg->username, perceived, reg->refresh, regstate2str(reg->regstate));
07115 counter++;
07116 }
07117 AST_LIST_UNLOCK(®istrations);
07118 ast_cli(a->fd, "%d IAX2 registrations.\n", counter);
07119 return CLI_SUCCESS;
07120 #undef FORMAT
07121 #undef FORMAT2
07122 }
07123
07124 static int manager_iax2_show_registry(struct mansession *s, const struct message *m)
07125 {
07126 const char *id = astman_get_header(m, "ActionID");
07127 struct iax2_registry *reg = NULL;
07128 char idtext[256] = "";
07129 char host[80] = "";
07130 char perceived[80] = "";
07131 int total = 0;
07132
07133 if (!ast_strlen_zero(id))
07134 snprintf(idtext, sizeof(idtext), "ActionID: %s\r\n", id);
07135
07136 astman_send_listack(s, m, "Registrations will follow", "start");
07137
07138 AST_LIST_LOCK(®istrations);
07139 AST_LIST_TRAVERSE(®istrations, reg, entry) {
07140 snprintf(host, sizeof(host), "%s", ast_sockaddr_stringify(®->addr));
07141
07142 if (reg->us.sin_addr.s_addr) {
07143 snprintf(perceived, sizeof(perceived), "%s:%d", ast_inet_ntoa(reg->us.sin_addr), ntohs(reg->us.sin_port));
07144 } else {
07145 ast_copy_string(perceived, "<Unregistered>", sizeof(perceived));
07146 }
07147
07148 astman_append(s,
07149 "Event: RegistryEntry\r\n"
07150 "%s"
07151 "Host: %s\r\n"
07152 "DNSmanager: %s\r\n"
07153 "Username: %s\r\n"
07154 "Perceived: %s\r\n"
07155 "Refresh: %d\r\n"
07156 "State: %s\r\n"
07157 "\r\n", idtext, host, (reg->dnsmgr) ? "Y" : "N", reg->username, perceived,
07158 reg->refresh, regstate2str(reg->regstate));
07159
07160 total++;
07161 }
07162 AST_LIST_UNLOCK(®istrations);
07163
07164 astman_append(s,
07165 "Event: RegistrationsComplete\r\n"
07166 "EventList: Complete\r\n"
07167 "ListItems: %d\r\n"
07168 "%s"
07169 "\r\n", total, idtext);
07170
07171 return 0;
07172 }
07173
07174 static char *handle_cli_iax2_show_channels(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
07175 {
07176 #define FORMAT2 "%-20.20s %-15.15s %-10.10s %-11.11s %-11.11s %-7.7s %-6.6s %-6.6s %s %s %9s\n"
07177 #define FORMAT "%-20.20s %-15.15s %-10.10s %5.5d/%5.5d %5.5d/%5.5d %-5.5dms %-4.4dms %-4.4dms %-6.6s %s%s %3s%s\n"
07178 #define FORMATB "%-20.20s %-15.15s %-10.10s %5.5d/%5.5d %5.5d/%5.5d [Native Bridged to ID=%5.5d]\n"
07179 int x;
07180 int numchans = 0;
07181 char first_message[10] = { 0, };
07182 char last_message[10] = { 0, };
07183
07184 switch (cmd) {
07185 case CLI_INIT:
07186 e->command = "iax2 show channels";
07187 e->usage =
07188 "Usage: iax2 show channels\n"
07189 " Lists all currently active IAX channels.\n";
07190 return NULL;
07191 case CLI_GENERATE:
07192 return NULL;
07193 }
07194
07195 if (a->argc != 3)
07196 return CLI_SHOWUSAGE;
07197 ast_cli(a->fd, FORMAT2, "Channel", "Peer", "Username", "ID (Lo/Rem)", "Seq (Tx/Rx)", "Lag", "Jitter", "JitBuf", "Format", "FirstMsg", "LastMsg");
07198 for (x = 0; x < ARRAY_LEN(iaxs); x++) {
07199 ast_mutex_lock(&iaxsl[x]);
07200 if (iaxs[x]) {
07201 int lag, jitter, localdelay;
07202 jb_info jbinfo;
07203 if (ast_test_flag64(iaxs[x], IAX_USEJITTERBUF)) {
07204 jb_getinfo(iaxs[x]->jb, &jbinfo);
07205 jitter = jbinfo.jitter;
07206 localdelay = jbinfo.current - jbinfo.min;
07207 } else {
07208 jitter = -1;
07209 localdelay = 0;
07210 }
07211
07212 iax_frame_subclass2str(iaxs[x]->first_iax_message & ~MARK_IAX_SUBCLASS_TX, first_message, sizeof(first_message));
07213 iax_frame_subclass2str(iaxs[x]->last_iax_message & ~MARK_IAX_SUBCLASS_TX, last_message, sizeof(last_message));
07214 lag = iaxs[x]->remote_rr.delay;
07215 ast_cli(a->fd, FORMAT,
07216 iaxs[x]->owner ? iaxs[x]->owner->name : "(None)",
07217 ast_inet_ntoa(iaxs[x]->addr.sin_addr),
07218 S_OR(iaxs[x]->username, "(None)"),
07219 iaxs[x]->callno, iaxs[x]->peercallno,
07220 iaxs[x]->oseqno, iaxs[x]->iseqno,
07221 lag,
07222 jitter,
07223 localdelay,
07224 ast_getformatname(iaxs[x]->voiceformat),
07225 (iaxs[x]->first_iax_message & MARK_IAX_SUBCLASS_TX) ? "Tx:" : "Rx:",
07226 first_message,
07227 (iaxs[x]->last_iax_message & MARK_IAX_SUBCLASS_TX) ? "Tx:" : "Rx:",
07228 last_message);
07229 numchans++;
07230 }
07231 ast_mutex_unlock(&iaxsl[x]);
07232 }
07233 ast_cli(a->fd, "%d active IAX channel%s\n", numchans, (numchans != 1) ? "s" : "");
07234 return CLI_SUCCESS;
07235 #undef FORMAT
07236 #undef FORMAT2
07237 #undef FORMATB
07238 }
07239
07240 static int ast_cli_netstats(struct mansession *s, int fd, int limit_fmt)
07241 {
07242 int x;
07243 int numchans = 0;
07244 char first_message[10] = { 0, };
07245 char last_message[10] = { 0, };
07246 #define ACN_FORMAT1 "%-20.25s %4d %4d %4d %5d %3d %5d %4d %6d %4d %4d %5d %3d %5d %4d %6d %s%s %4s%s\n"
07247 #define ACN_FORMAT2 "%s %d %d %d %d %d %d %d %d %d %d %d %d %d %d %d %s%s %s%s\n"
07248 for (x = 0; x < ARRAY_LEN(iaxs); x++) {
07249 ast_mutex_lock(&iaxsl[x]);
07250 if (iaxs[x]) {
07251 int localjitter, localdelay, locallost, locallosspct, localdropped, localooo;
07252 jb_info jbinfo;
07253 iax_frame_subclass2str(iaxs[x]->first_iax_message & ~MARK_IAX_SUBCLASS_TX, first_message, sizeof(first_message));
07254 iax_frame_subclass2str(iaxs[x]->last_iax_message & ~MARK_IAX_SUBCLASS_TX, last_message, sizeof(last_message));
07255
07256 if(ast_test_flag64(iaxs[x], IAX_USEJITTERBUF)) {
07257 jb_getinfo(iaxs[x]->jb, &jbinfo);
07258 localjitter = jbinfo.jitter;
07259 localdelay = jbinfo.current - jbinfo.min;
07260 locallost = jbinfo.frames_lost;
07261 locallosspct = jbinfo.losspct/1000;
07262 localdropped = jbinfo.frames_dropped;
07263 localooo = jbinfo.frames_ooo;
07264 } else {
07265 localjitter = -1;
07266 localdelay = 0;
07267 locallost = -1;
07268 locallosspct = -1;
07269 localdropped = 0;
07270 localooo = -1;
07271 }
07272 if (s)
07273 astman_append(s, limit_fmt ? ACN_FORMAT1 : ACN_FORMAT2,
07274 iaxs[x]->owner ? iaxs[x]->owner->name : "(None)",
07275 iaxs[x]->pingtime,
07276 localjitter,
07277 localdelay,
07278 locallost,
07279 locallosspct,
07280 localdropped,
07281 localooo,
07282 iaxs[x]->frames_received/1000,
07283 iaxs[x]->remote_rr.jitter,
07284 iaxs[x]->remote_rr.delay,
07285 iaxs[x]->remote_rr.losscnt,
07286 iaxs[x]->remote_rr.losspct,
07287 iaxs[x]->remote_rr.dropped,
07288 iaxs[x]->remote_rr.ooo,
07289 iaxs[x]->remote_rr.packets/1000,
07290 (iaxs[x]->first_iax_message & MARK_IAX_SUBCLASS_TX) ? "Tx:" : "Rx:",
07291 first_message,
07292 (iaxs[x]->last_iax_message & MARK_IAX_SUBCLASS_TX) ? "Tx:" : "Rx:",
07293 last_message);
07294 else
07295 ast_cli(fd, limit_fmt ? ACN_FORMAT1 : ACN_FORMAT2,
07296 iaxs[x]->owner ? iaxs[x]->owner->name : "(None)",
07297 iaxs[x]->pingtime,
07298 localjitter,
07299 localdelay,
07300 locallost,
07301 locallosspct,
07302 localdropped,
07303 localooo,
07304 iaxs[x]->frames_received/1000,
07305 iaxs[x]->remote_rr.jitter,
07306 iaxs[x]->remote_rr.delay,
07307 iaxs[x]->remote_rr.losscnt,
07308 iaxs[x]->remote_rr.losspct,
07309 iaxs[x]->remote_rr.dropped,
07310 iaxs[x]->remote_rr.ooo,
07311 iaxs[x]->remote_rr.packets/1000,
07312 (iaxs[x]->first_iax_message & MARK_IAX_SUBCLASS_TX) ? "Tx:" : "Rx:",
07313 first_message,
07314 (iaxs[x]->last_iax_message & MARK_IAX_SUBCLASS_TX) ? "Tx:" : "Rx:",
07315 last_message);
07316 numchans++;
07317 }
07318 ast_mutex_unlock(&iaxsl[x]);
07319 }
07320
07321 return numchans;
07322 }
07323
07324 static char *handle_cli_iax2_show_netstats(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
07325 {
07326 int numchans = 0;
07327
07328 switch (cmd) {
07329 case CLI_INIT:
07330 e->command = "iax2 show netstats";
07331 e->usage =
07332 "Usage: iax2 show netstats\n"
07333 " Lists network status for all currently active IAX channels.\n";
07334 return NULL;
07335 case CLI_GENERATE:
07336 return NULL;
07337 }
07338 if (a->argc != 3)
07339 return CLI_SHOWUSAGE;
07340 ast_cli(a->fd, " -------- LOCAL --------------------- -------- REMOTE --------------------\n");
07341 ast_cli(a->fd, "Channel RTT Jit Del Lost %% Drop OOO Kpkts Jit Del Lost %% Drop OOO Kpkts FirstMsg LastMsg\n");
07342 numchans = ast_cli_netstats(NULL, a->fd, 1);
07343 ast_cli(a->fd, "%d active IAX channel%s\n", numchans, (numchans != 1) ? "s" : "");
07344 return CLI_SUCCESS;
07345 }
07346
07347 static char *handle_cli_iax2_set_debug(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
07348 {
07349 switch (cmd) {
07350 case CLI_INIT:
07351 e->command = "iax2 set debug {on|off|peer}";
07352 e->usage =
07353 "Usage: iax2 set debug {on|off|peer peername}\n"
07354 " Enables/Disables dumping of IAX packets for debugging purposes.\n";
07355 return NULL;
07356 case CLI_GENERATE:
07357 if (a->pos == 4 && !strcasecmp(a->argv[3], "peer"))
07358 return complete_iax2_peers(a->line, a->word, a->pos, a->n, 0);
07359 return NULL;
07360 }
07361
07362 if (a->argc < e->args || a->argc > e->args + 1)
07363 return CLI_SHOWUSAGE;
07364
07365 if (!strcasecmp(a->argv[3], "peer")) {
07366 struct iax2_peer *peer;
07367 struct sockaddr_in peer_addr;
07368
07369
07370 if (a->argc != e->args + 1)
07371 return CLI_SHOWUSAGE;
07372
07373 peer = find_peer(a->argv[4], 1);
07374
07375 if (!peer) {
07376 ast_cli(a->fd, "IAX2 peer '%s' does not exist\n", a->argv[e->args-1]);
07377 return CLI_FAILURE;
07378 }
07379
07380 ast_sockaddr_to_sin(&peer->addr, &peer_addr);
07381
07382 debugaddr.sin_addr = peer_addr.sin_addr;
07383 debugaddr.sin_port = peer_addr.sin_port;
07384
07385 ast_cli(a->fd, "IAX2 Debugging Enabled for IP: %s:%d\n",
07386 ast_inet_ntoa(debugaddr.sin_addr), ntohs(debugaddr.sin_port));
07387
07388 ao2_ref(peer, -1);
07389 } else if (!strncasecmp(a->argv[3], "on", 2)) {
07390 iaxdebug = 1;
07391 ast_cli(a->fd, "IAX2 Debugging Enabled\n");
07392 } else {
07393 iaxdebug = 0;
07394 memset(&debugaddr, 0, sizeof(debugaddr));
07395 ast_cli(a->fd, "IAX2 Debugging Disabled\n");
07396 }
07397 return CLI_SUCCESS;
07398 }
07399
07400 static char *handle_cli_iax2_set_debug_trunk(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
07401 {
07402 switch (cmd) {
07403 case CLI_INIT:
07404 e->command = "iax2 set debug trunk {on|off}";
07405 e->usage =
07406 "Usage: iax2 set debug trunk {on|off}\n"
07407 " Enables/Disables debugging of IAX trunking\n";
07408 return NULL;
07409 case CLI_GENERATE:
07410 return NULL;
07411 }
07412
07413 if (a->argc != e->args)
07414 return CLI_SHOWUSAGE;
07415
07416 if (!strncasecmp(a->argv[e->args - 1], "on", 2)) {
07417 iaxtrunkdebug = 1;
07418 ast_cli(a->fd, "IAX2 Trunk Debugging Enabled\n");
07419 } else {
07420 iaxtrunkdebug = 0;
07421 ast_cli(a->fd, "IAX2 Trunk Debugging Disabled\n");
07422 }
07423 return CLI_SUCCESS;
07424 }
07425
07426 static char *handle_cli_iax2_set_debug_jb(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
07427 {
07428 switch (cmd) {
07429 case CLI_INIT:
07430 e->command = "iax2 set debug jb {on|off}";
07431 e->usage =
07432 "Usage: iax2 set debug jb {on|off}\n"
07433 " Enables/Disables jitterbuffer debugging information\n";
07434 return NULL;
07435 case CLI_GENERATE:
07436 return NULL;
07437 }
07438
07439 if (a->argc != e->args)
07440 return CLI_SHOWUSAGE;
07441
07442 if (!strncasecmp(a->argv[e->args -1], "on", 2)) {
07443 jb_setoutput(jb_error_output, jb_warning_output, jb_debug_output);
07444 ast_cli(a->fd, "IAX2 Jitterbuffer Debugging Enabled\n");
07445 } else {
07446 jb_setoutput(jb_error_output, jb_warning_output, NULL);
07447 ast_cli(a->fd, "IAX2 Jitterbuffer Debugging Disabled\n");
07448 }
07449 return CLI_SUCCESS;
07450 }
07451
07452 static int iax2_write(struct ast_channel *c, struct ast_frame *f)
07453 {
07454 unsigned short callno = PTR_TO_CALLNO(c->tech_pvt);
07455 int res = -1;
07456 ast_mutex_lock(&iaxsl[callno]);
07457 if (iaxs[callno]) {
07458
07459 if (!iaxs[callno]->error) {
07460 if (ast_test_flag64(iaxs[callno], IAX_ALREADYGONE))
07461 res = 0;
07462
07463 else if (f->frametype == AST_FRAME_NULL)
07464 res = 0;
07465 else if ((f->frametype == AST_FRAME_VOICE) && ast_test_flag64(iaxs[callno], IAX_QUELCH))
07466 res = 0;
07467 else if (!ast_test_flag(&iaxs[callno]->state, IAX_STATE_STARTED))
07468 res = 0;
07469 else
07470
07471 res = iax2_send(iaxs[callno], f, 0, -1, 0, 0, 0);
07472 } else {
07473 ast_debug(1, "Write error: %s\n", strerror(errno));
07474 }
07475 }
07476
07477 ast_mutex_unlock(&iaxsl[callno]);
07478 return res;
07479 }
07480
07481 static int __send_command(struct chan_iax2_pvt *i, char type, int command, unsigned int ts, const unsigned char *data, int datalen, int seqno,
07482 int now, int transfer, int final)
07483 {
07484 struct ast_frame f = { 0, };
07485 int res = 0;
07486
07487 f.frametype = type;
07488 f.subclass.integer = command;
07489 f.datalen = datalen;
07490 f.src = __FUNCTION__;
07491 f.data.ptr = (void *) data;
07492
07493 if ((res = queue_signalling(i, &f)) <= 0) {
07494 return res;
07495 }
07496
07497 return iax2_send(i, &f, ts, seqno, now, transfer, final);
07498 }
07499
07500 static int send_command(struct chan_iax2_pvt *i, char type, int command, unsigned int ts, const unsigned char *data, int datalen, int seqno)
07501 {
07502 return __send_command(i, type, command, ts, data, datalen, seqno, 0, 0, 0);
07503 }
07504
07505 static int send_command_locked(unsigned short callno, char type, int command, unsigned int ts, const unsigned char *data, int datalen, int seqno)
07506 {
07507 int res;
07508 ast_mutex_lock(&iaxsl[callno]);
07509 res = send_command(iaxs[callno], type, command, ts, data, datalen, seqno);
07510 ast_mutex_unlock(&iaxsl[callno]);
07511 return res;
07512 }
07513
07514
07515
07516
07517
07518
07519 static int send_command_final(struct chan_iax2_pvt *i, char type, int command, unsigned int ts, const unsigned char *data, int datalen, int seqno)
07520 {
07521 int call_num = i->callno;
07522
07523 iax2_predestroy(i->callno);
07524 if (!iaxs[call_num])
07525 return -1;
07526 return __send_command(i, type, command, ts, data, datalen, seqno, 0, 0, 1);
07527 }
07528
07529 static int send_command_immediate(struct chan_iax2_pvt *i, char type, int command, unsigned int ts, const unsigned char *data, int datalen, int seqno)
07530 {
07531 return __send_command(i, type, command, ts, data, datalen, seqno, 1, 0, 0);
07532 }
07533
07534 static int send_command_transfer(struct chan_iax2_pvt *i, char type, int command, unsigned int ts, const unsigned char *data, int datalen)
07535 {
07536 return __send_command(i, type, command, ts, data, datalen, 0, 0, 1, 0);
07537 }
07538
07539 static int apply_context(struct iax2_context *con, const char *context)
07540 {
07541 while(con) {
07542 if (!strcmp(con->context, context) || !strcmp(con->context, "*"))
07543 return -1;
07544 con = con->next;
07545 }
07546 return 0;
07547 }
07548
07549
07550 static int check_access(int callno, struct sockaddr_in *sin, struct iax_ies *ies)
07551 {
07552
07553 int res = -1;
07554 int version = 2;
07555 struct iax2_user *user = NULL, *best = NULL;
07556 int bestscore = 0;
07557 int gotcapability = 0;
07558 struct ast_variable *v = NULL, *tmpvar = NULL;
07559 struct ao2_iterator i;
07560 struct ast_sockaddr addr;
07561
07562 if (!iaxs[callno])
07563 return res;
07564 if (ies->called_number)
07565 ast_string_field_set(iaxs[callno], exten, ies->called_number);
07566 if (ies->calling_number) {
07567 if (ast_test_flag64(&globalflags, IAX_SHRINKCALLERID)) {
07568 ast_shrink_phone_number(ies->calling_number);
07569 }
07570 ast_string_field_set(iaxs[callno], cid_num, ies->calling_number);
07571 }
07572 if (ies->calling_name)
07573 ast_string_field_set(iaxs[callno], cid_name, ies->calling_name);
07574 if (ies->calling_ani)
07575 ast_string_field_set(iaxs[callno], ani, ies->calling_ani);
07576 if (ies->dnid)
07577 ast_string_field_set(iaxs[callno], dnid, ies->dnid);
07578 if (ies->rdnis)
07579 ast_string_field_set(iaxs[callno], rdnis, ies->rdnis);
07580 if (ies->called_context)
07581 ast_string_field_set(iaxs[callno], context, ies->called_context);
07582 if (ies->language)
07583 ast_string_field_set(iaxs[callno], language, ies->language);
07584 if (ies->username)
07585 ast_string_field_set(iaxs[callno], username, ies->username);
07586 if (ies->calling_ton > -1)
07587 iaxs[callno]->calling_ton = ies->calling_ton;
07588 if (ies->calling_tns > -1)
07589 iaxs[callno]->calling_tns = ies->calling_tns;
07590 if (ies->calling_pres > -1)
07591 iaxs[callno]->calling_pres = ies->calling_pres;
07592 if (ies->format)
07593 iaxs[callno]->peerformat = ies->format;
07594 if (ies->adsicpe)
07595 iaxs[callno]->peeradsicpe = ies->adsicpe;
07596 if (ies->capability) {
07597 gotcapability = 1;
07598 iaxs[callno]->peercapability = ies->capability;
07599 }
07600 if (ies->version)
07601 version = ies->version;
07602
07603
07604 if (ies->codec_prefs) {
07605 ast_codec_pref_convert(&iaxs[callno]->rprefs, ies->codec_prefs, 32, 0);
07606 ast_codec_pref_convert(&iaxs[callno]->prefs, ies->codec_prefs, 32, 0);
07607 }
07608
07609 if (!gotcapability)
07610 iaxs[callno]->peercapability = iaxs[callno]->peerformat;
07611 if (version > IAX_PROTO_VERSION) {
07612 ast_log(LOG_WARNING, "Peer '%s' has too new a protocol version (%d) for me\n",
07613 ast_inet_ntoa(sin->sin_addr), version);
07614 return res;
07615 }
07616
07617 ast_sockaddr_from_sin(&addr, sin);
07618 i = ao2_iterator_init(users, 0);
07619 while ((user = ao2_iterator_next(&i))) {
07620 if ((ast_strlen_zero(iaxs[callno]->username) ||
07621 !strcmp(iaxs[callno]->username, user->name))
07622 && ast_apply_ha(user->ha, &addr) == AST_SENSE_ALLOW
07623 && (ast_strlen_zero(iaxs[callno]->context) ||
07624 apply_context(user->contexts, iaxs[callno]->context))) {
07625 if (!ast_strlen_zero(iaxs[callno]->username)) {
07626
07627 if (best)
07628 user_unref(best);
07629 best = user;
07630 break;
07631 } else if (ast_strlen_zero(user->secret) && ast_strlen_zero(user->dbsecret) && ast_strlen_zero(user->inkeys)) {
07632
07633 if (user->ha) {
07634
07635 if (bestscore < 4) {
07636 bestscore = 4;
07637 if (best)
07638 user_unref(best);
07639 best = user;
07640 continue;
07641 }
07642 } else {
07643
07644 if (bestscore < 3) {
07645 bestscore = 3;
07646 if (best)
07647 user_unref(best);
07648 best = user;
07649 continue;
07650 }
07651 }
07652 } else {
07653 if (user->ha) {
07654
07655 if (bestscore < 2) {
07656 bestscore = 2;
07657 if (best)
07658 user_unref(best);
07659 best = user;
07660 continue;
07661 }
07662 } else {
07663
07664 if (bestscore < 1) {
07665 bestscore = 1;
07666 if (best)
07667 user_unref(best);
07668 best = user;
07669 continue;
07670 }
07671 }
07672 }
07673 }
07674 user_unref(user);
07675 }
07676 ao2_iterator_destroy(&i);
07677 user = best;
07678 if (!user && !ast_strlen_zero(iaxs[callno]->username)) {
07679 user = realtime_user(iaxs[callno]->username, sin);
07680 if (user && (ast_apply_ha(user->ha, &addr) == AST_SENSE_DENY
07681 || (!ast_strlen_zero(iaxs[callno]->context) &&
07682 !apply_context(user->contexts, iaxs[callno]->context)))) {
07683 user = user_unref(user);
07684 }
07685 }
07686 if (user) {
07687
07688
07689 for (v = user->vars ; v ; v = v->next) {
07690 if((tmpvar = ast_variable_new(v->name, v->value, v->file))) {
07691 tmpvar->next = iaxs[callno]->vars;
07692 iaxs[callno]->vars = tmpvar;
07693 }
07694 }
07695
07696 if (user->maxauthreq > 0)
07697 ast_set_flag64(iaxs[callno], IAX_MAXAUTHREQ);
07698 iaxs[callno]->prefs = user->prefs;
07699 ast_copy_flags64(iaxs[callno], user, IAX_CODEC_USER_FIRST | IAX_IMMEDIATE | IAX_CODEC_NOPREFS | IAX_CODEC_NOCAP | IAX_FORCE_ENCRYPT);
07700 iaxs[callno]->encmethods = user->encmethods;
07701
07702 if (ast_strlen_zero(iaxs[callno]->username))
07703 ast_string_field_set(iaxs[callno], username, user->name);
07704
07705 ast_copy_flags64(iaxs[callno], user, IAX_TRUNK);
07706 iaxs[callno]->capability = user->capability;
07707
07708 if (ast_strlen_zero(iaxs[callno]->context)) {
07709 if (user->contexts)
07710 ast_string_field_set(iaxs[callno], context, user->contexts->context);
07711 else
07712 ast_string_field_set(iaxs[callno], context, DEFAULT_CONTEXT);
07713 }
07714
07715 ast_string_field_set(iaxs[callno], inkeys, user->inkeys);
07716
07717 iaxs[callno]->authmethods = user->authmethods;
07718 iaxs[callno]->adsi = user->adsi;
07719
07720 if (ast_test_flag64(user, IAX_HASCALLERID)) {
07721 iaxs[callno]->calling_tns = 0;
07722 iaxs[callno]->calling_ton = 0;
07723 ast_string_field_set(iaxs[callno], cid_num, user->cid_num);
07724 ast_string_field_set(iaxs[callno], cid_name, user->cid_name);
07725 ast_string_field_set(iaxs[callno], ani, user->cid_num);
07726 iaxs[callno]->calling_pres = AST_PRES_ALLOWED_USER_NUMBER_PASSED_SCREEN;
07727 } else if (ast_strlen_zero(iaxs[callno]->cid_num) && ast_strlen_zero(iaxs[callno]->cid_name)) {
07728 iaxs[callno]->calling_pres = AST_PRES_NUMBER_NOT_AVAILABLE;
07729 }
07730 if (!ast_strlen_zero(user->accountcode))
07731 ast_string_field_set(iaxs[callno], accountcode, user->accountcode);
07732 if (!ast_strlen_zero(user->mohinterpret))
07733 ast_string_field_set(iaxs[callno], mohinterpret, user->mohinterpret);
07734 if (!ast_strlen_zero(user->mohsuggest))
07735 ast_string_field_set(iaxs[callno], mohsuggest, user->mohsuggest);
07736 if (!ast_strlen_zero(user->parkinglot))
07737 ast_string_field_set(iaxs[callno], parkinglot, user->parkinglot);
07738 if (user->amaflags)
07739 iaxs[callno]->amaflags = user->amaflags;
07740 if (!ast_strlen_zero(user->language))
07741 ast_string_field_set(iaxs[callno], language, user->language);
07742 ast_copy_flags64(iaxs[callno], user, IAX_NOTRANSFER | IAX_TRANSFERMEDIA | IAX_USEJITTERBUF | IAX_FORCEJITTERBUF | IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
07743
07744 if (!ast_strlen_zero(user->dbsecret)) {
07745 char *family, *key=NULL;
07746 char buf[80];
07747 family = ast_strdupa(user->dbsecret);
07748 key = strchr(family, '/');
07749 if (key) {
07750 *key = '\0';
07751 key++;
07752 }
07753 if (!key || ast_db_get(family, key, buf, sizeof(buf)))
07754 ast_log(LOG_WARNING, "Unable to retrieve database password for family/key '%s'!\n", user->dbsecret);
07755 else
07756 ast_string_field_set(iaxs[callno], secret, buf);
07757 } else
07758 ast_string_field_set(iaxs[callno], secret, user->secret);
07759 res = 0;
07760 user = user_unref(user);
07761 } else {
07762
07763
07764
07765
07766 iaxs[callno]->authmethods = last_authmethod ? last_authmethod : (IAX_AUTH_MD5 | IAX_AUTH_PLAINTEXT);
07767 ast_string_field_set(iaxs[callno], secret, "badsecret");
07768 iaxs[callno]->authrej = 1;
07769 if (!ast_strlen_zero(iaxs[callno]->username)) {
07770
07771 res = 0;
07772 }
07773 }
07774 ast_set2_flag64(iaxs[callno], iax2_getpeertrunk(*sin), IAX_TRUNK);
07775 return res;
07776 }
07777
07778 static int raw_hangup(struct sockaddr_in *sin, unsigned short src, unsigned short dst, int sockfd)
07779 {
07780 struct ast_iax2_full_hdr fh;
07781 fh.scallno = htons(src | IAX_FLAG_FULL);
07782 fh.dcallno = htons(dst);
07783 fh.ts = 0;
07784 fh.oseqno = 0;
07785 fh.iseqno = 0;
07786 fh.type = AST_FRAME_IAX;
07787 fh.csub = compress_subclass(IAX_COMMAND_INVAL);
07788 iax_outputframe(NULL, &fh, 0, sin, 0);
07789 #if 0
07790 if (option_debug)
07791 #endif
07792 ast_debug(1, "Raw Hangup %s:%d, src=%d, dst=%d\n",
07793 ast_inet_ntoa(sin->sin_addr), ntohs(sin->sin_port), src, dst);
07794 return sendto(sockfd, &fh, sizeof(fh), 0, (struct sockaddr *)sin, sizeof(*sin));
07795 }
07796
07797 static void merge_encryption(struct chan_iax2_pvt *p, unsigned int enc)
07798 {
07799
07800 p->encmethods &= enc;
07801 if (p->encmethods) {
07802 if (!(p->encmethods & IAX_ENCRYPT_KEYROTATE)){
07803 p->keyrotateid = -2;
07804 }
07805 if (p->encmethods & IAX_ENCRYPT_AES128)
07806 p->encmethods = IAX_ENCRYPT_AES128;
07807 else
07808 p->encmethods = 0;
07809 }
07810 }
07811
07812
07813
07814
07815
07816
07817
07818 static int authenticate_request(int call_num)
07819 {
07820 struct iax_ie_data ied;
07821 int res = -1, authreq_restrict = 0;
07822 char challenge[10];
07823 struct chan_iax2_pvt *p = iaxs[call_num];
07824
07825 memset(&ied, 0, sizeof(ied));
07826
07827
07828 if (ast_test_flag64(p, IAX_MAXAUTHREQ)) {
07829 struct iax2_user *user, tmp_user = {
07830 .name = p->username,
07831 };
07832
07833 user = ao2_find(users, &tmp_user, OBJ_POINTER);
07834 if (user) {
07835 if (user->curauthreq == user->maxauthreq)
07836 authreq_restrict = 1;
07837 else
07838 user->curauthreq++;
07839 user = user_unref(user);
07840 }
07841 }
07842
07843
07844 if (authreq_restrict) {
07845 iax_ie_append_str(&ied, IAX_IE_CAUSE, "Unauthenticated call limit reached");
07846 iax_ie_append_byte(&ied, IAX_IE_CAUSECODE, AST_CAUSE_CALL_REJECTED);
07847 send_command_final(p, AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied.buf, ied.pos, -1);
07848 return 0;
07849 }
07850
07851 iax_ie_append_short(&ied, IAX_IE_AUTHMETHODS, p->authmethods);
07852 if (p->authmethods & (IAX_AUTH_MD5 | IAX_AUTH_RSA)) {
07853 snprintf(challenge, sizeof(challenge), "%d", (int)ast_random());
07854 ast_string_field_set(p, challenge, challenge);
07855
07856 iax_ie_append_str(&ied, IAX_IE_CHALLENGE, p->challenge);
07857 }
07858 if (p->encmethods)
07859 iax_ie_append_short(&ied, IAX_IE_ENCRYPTION, p->encmethods);
07860
07861 iax_ie_append_str(&ied,IAX_IE_USERNAME, p->username);
07862
07863 res = send_command(p, AST_FRAME_IAX, IAX_COMMAND_AUTHREQ, 0, ied.buf, ied.pos, -1);
07864
07865 if (p->encmethods)
07866 ast_set_flag64(p, IAX_ENCRYPTED);
07867
07868 return res;
07869 }
07870
07871 static int authenticate_verify(struct chan_iax2_pvt *p, struct iax_ies *ies)
07872 {
07873 char requeststr[256];
07874 char md5secret[256] = "";
07875 char secret[256] = "";
07876 char rsasecret[256] = "";
07877 int res = -1;
07878 int x;
07879 struct iax2_user *user, tmp_user = {
07880 .name = p->username,
07881 };
07882
07883 if (p->authrej) {
07884 return res;
07885 }
07886 user = ao2_find(users, &tmp_user, OBJ_POINTER);
07887 if (user) {
07888 if (ast_test_flag64(p, IAX_MAXAUTHREQ)) {
07889 ast_atomic_fetchadd_int(&user->curauthreq, -1);
07890 ast_clear_flag64(p, IAX_MAXAUTHREQ);
07891 }
07892 ast_string_field_set(p, host, user->name);
07893 user = user_unref(user);
07894 }
07895 if (ast_test_flag64(p, IAX_FORCE_ENCRYPT) && !p->encmethods) {
07896 ast_log(LOG_NOTICE, "Call Terminated, Incoming call is unencrypted while force encrypt is enabled.\n");
07897 return res;
07898 }
07899 if (!ast_test_flag(&p->state, IAX_STATE_AUTHENTICATED))
07900 return res;
07901 if (ies->password)
07902 ast_copy_string(secret, ies->password, sizeof(secret));
07903 if (ies->md5_result)
07904 ast_copy_string(md5secret, ies->md5_result, sizeof(md5secret));
07905 if (ies->rsa_result)
07906 ast_copy_string(rsasecret, ies->rsa_result, sizeof(rsasecret));
07907 if ((p->authmethods & IAX_AUTH_RSA) && !ast_strlen_zero(rsasecret) && !ast_strlen_zero(p->inkeys)) {
07908 struct ast_key *key;
07909 char *keyn;
07910 char tmpkey[256];
07911 char *stringp=NULL;
07912 ast_copy_string(tmpkey, p->inkeys, sizeof(tmpkey));
07913 stringp=tmpkey;
07914 keyn = strsep(&stringp, ":");
07915 while(keyn) {
07916 key = ast_key_get(keyn, AST_KEY_PUBLIC);
07917 if (key && !ast_check_signature(key, p->challenge, rsasecret)) {
07918 res = 0;
07919 break;
07920 } else if (!key)
07921 ast_log(LOG_WARNING, "requested inkey '%s' for RSA authentication does not exist\n", keyn);
07922 keyn = strsep(&stringp, ":");
07923 }
07924 } else if (p->authmethods & IAX_AUTH_MD5) {
07925 struct MD5Context md5;
07926 unsigned char digest[16];
07927 char *tmppw, *stringp;
07928
07929 tmppw = ast_strdupa(p->secret);
07930 stringp = tmppw;
07931 while((tmppw = strsep(&stringp, ";"))) {
07932 MD5Init(&md5);
07933 MD5Update(&md5, (unsigned char *)p->challenge, strlen(p->challenge));
07934 MD5Update(&md5, (unsigned char *)tmppw, strlen(tmppw));
07935 MD5Final(digest, &md5);
07936
07937 for (x=0;x<16;x++)
07938 sprintf(requeststr + (x << 1), "%2.2x", digest[x]);
07939 if (!strcasecmp(requeststr, md5secret)) {
07940 res = 0;
07941 break;
07942 }
07943 }
07944 } else if (p->authmethods & IAX_AUTH_PLAINTEXT) {
07945 if (!strcmp(secret, p->secret))
07946 res = 0;
07947 }
07948 return res;
07949 }
07950
07951
07952 static int register_verify(int callno, struct sockaddr_in *sin, struct iax_ies *ies)
07953 {
07954 char requeststr[256] = "";
07955 char peer[256] = "";
07956 char md5secret[256] = "";
07957 char rsasecret[256] = "";
07958 char secret[256] = "";
07959 struct iax2_peer *p = NULL;
07960 struct ast_key *key;
07961 char *keyn;
07962 int x;
07963 int expire = 0;
07964 int res = -1;
07965 struct ast_sockaddr addr;
07966
07967 ast_clear_flag(&iaxs[callno]->state, IAX_STATE_AUTHENTICATED);
07968
07969 if (ies->username)
07970 ast_copy_string(peer, ies->username, sizeof(peer));
07971 if (ies->password)
07972 ast_copy_string(secret, ies->password, sizeof(secret));
07973 if (ies->md5_result)
07974 ast_copy_string(md5secret, ies->md5_result, sizeof(md5secret));
07975 if (ies->rsa_result)
07976 ast_copy_string(rsasecret, ies->rsa_result, sizeof(rsasecret));
07977 if (ies->refresh)
07978 expire = ies->refresh;
07979
07980 if (ast_strlen_zero(peer)) {
07981 ast_log(LOG_NOTICE, "Empty registration from %s\n", ast_inet_ntoa(sin->sin_addr));
07982 return -1;
07983 }
07984
07985
07986 ast_mutex_unlock(&iaxsl[callno]);
07987 p = find_peer(peer, 1);
07988 ast_mutex_lock(&iaxsl[callno]);
07989 if (!p || !iaxs[callno]) {
07990 if (iaxs[callno]) {
07991 int plaintext = ((last_authmethod & IAX_AUTH_PLAINTEXT) | (iaxs[callno]->authmethods & IAX_AUTH_PLAINTEXT));
07992
07993 ast_string_field_set(iaxs[callno], secret, "badsecret");
07994
07995
07996
07997
07998
07999
08000
08001
08002
08003 if (ast_strlen_zero(iaxs[callno]->challenge) &&
08004 !(!ast_strlen_zero(secret) && plaintext)) {
08005
08006 res = 0;
08007 }
08008 }
08009 if (authdebug && !p)
08010 ast_log(LOG_NOTICE, "No registration for peer '%s' (from %s)\n", peer, ast_inet_ntoa(sin->sin_addr));
08011 goto return_unref;
08012 }
08013
08014 if (!ast_test_flag64(p, IAX_DYNAMIC)) {
08015 if (authdebug)
08016 ast_log(LOG_NOTICE, "Peer '%s' is not dynamic (from %s)\n", peer, ast_inet_ntoa(sin->sin_addr));
08017 goto return_unref;
08018 }
08019
08020 ast_sockaddr_from_sin(&addr, sin);
08021 if (!ast_apply_ha(p->ha, &addr)) {
08022 if (authdebug)
08023 ast_log(LOG_NOTICE, "Host %s denied access to register peer '%s'\n", ast_inet_ntoa(sin->sin_addr), p->name);
08024 goto return_unref;
08025 }
08026 ast_string_field_set(iaxs[callno], secret, p->secret);
08027 ast_string_field_set(iaxs[callno], inkeys, p->inkeys);
08028
08029 if (!ast_strlen_zero(rsasecret) && (p->authmethods & IAX_AUTH_RSA) && !ast_strlen_zero(iaxs[callno]->challenge)) {
08030 if (!ast_strlen_zero(p->inkeys)) {
08031 char tmpkeys[256];
08032 char *stringp=NULL;
08033 ast_copy_string(tmpkeys, p->inkeys, sizeof(tmpkeys));
08034 stringp=tmpkeys;
08035 keyn = strsep(&stringp, ":");
08036 while(keyn) {
08037 key = ast_key_get(keyn, AST_KEY_PUBLIC);
08038 if (key && !ast_check_signature(key, iaxs[callno]->challenge, rsasecret)) {
08039 ast_set_flag(&iaxs[callno]->state, IAX_STATE_AUTHENTICATED);
08040 break;
08041 } else if (!key)
08042 ast_log(LOG_WARNING, "requested inkey '%s' does not exist\n", keyn);
08043 keyn = strsep(&stringp, ":");
08044 }
08045 if (!keyn) {
08046 if (authdebug)
08047 ast_log(LOG_NOTICE, "Host %s failed RSA authentication with inkeys '%s'\n", peer, p->inkeys);
08048 goto return_unref;
08049 }
08050 } else {
08051 if (authdebug)
08052 ast_log(LOG_NOTICE, "Host '%s' trying to do RSA authentication, but we have no inkeys\n", peer);
08053 goto return_unref;
08054 }
08055 } else if (!ast_strlen_zero(md5secret) && (p->authmethods & IAX_AUTH_MD5) && !ast_strlen_zero(iaxs[callno]->challenge)) {
08056 struct MD5Context md5;
08057 unsigned char digest[16];
08058 char *tmppw, *stringp;
08059
08060 tmppw = ast_strdupa(p->secret);
08061 stringp = tmppw;
08062 while((tmppw = strsep(&stringp, ";"))) {
08063 MD5Init(&md5);
08064 MD5Update(&md5, (unsigned char *)iaxs[callno]->challenge, strlen(iaxs[callno]->challenge));
08065 MD5Update(&md5, (unsigned char *)tmppw, strlen(tmppw));
08066 MD5Final(digest, &md5);
08067 for (x=0;x<16;x++)
08068 sprintf(requeststr + (x << 1), "%2.2x", digest[x]);
08069 if (!strcasecmp(requeststr, md5secret))
08070 break;
08071 }
08072 if (tmppw) {
08073 ast_set_flag(&iaxs[callno]->state, IAX_STATE_AUTHENTICATED);
08074 } else {
08075 if (authdebug)
08076 ast_log(LOG_NOTICE, "Host %s failed MD5 authentication for '%s' (%s != %s)\n", ast_inet_ntoa(sin->sin_addr), p->name, requeststr, md5secret);
08077 goto return_unref;
08078 }
08079 } else if (!ast_strlen_zero(secret) && (p->authmethods & IAX_AUTH_PLAINTEXT)) {
08080
08081 if (strcmp(secret, p->secret)) {
08082 if (authdebug)
08083 ast_log(LOG_NOTICE, "Host %s did not provide proper plaintext password for '%s'\n", ast_inet_ntoa(sin->sin_addr), p->name);
08084 goto return_unref;
08085 } else
08086 ast_set_flag(&iaxs[callno]->state, IAX_STATE_AUTHENTICATED);
08087 } else if (!ast_strlen_zero(iaxs[callno]->challenge) && ast_strlen_zero(md5secret) && ast_strlen_zero(rsasecret)) {
08088
08089 goto return_unref;
08090 }
08091 ast_devstate_changed(AST_DEVICE_UNKNOWN, "IAX2/%s", p->name);
08092
08093
08094 res = 0;
08095
08096 return_unref:
08097 if (iaxs[callno]) {
08098 ast_string_field_set(iaxs[callno], peer, peer);
08099
08100
08101 if (expire && (expire < iaxs[callno]->expiry)) {
08102 iaxs[callno]->expiry = expire;
08103 }
08104 }
08105
08106 if (p) {
08107 peer_unref(p);
08108 }
08109 return res;
08110 }
08111
08112 static int authenticate(const char *challenge, const char *secret, const char *keyn, int authmethods, struct iax_ie_data *ied, struct sockaddr_in *sin, struct chan_iax2_pvt *pvt)
08113 {
08114 int res = -1;
08115 int x;
08116 if (!ast_strlen_zero(keyn)) {
08117 if (!(authmethods & IAX_AUTH_RSA)) {
08118 if (ast_strlen_zero(secret))
08119 ast_log(LOG_NOTICE, "Asked to authenticate to %s with an RSA key, but they don't allow RSA authentication\n", ast_inet_ntoa(sin->sin_addr));
08120 } else if (ast_strlen_zero(challenge)) {
08121 ast_log(LOG_NOTICE, "No challenge provided for RSA authentication to %s\n", ast_inet_ntoa(sin->sin_addr));
08122 } else {
08123 char sig[256];
08124 struct ast_key *key;
08125 key = ast_key_get(keyn, AST_KEY_PRIVATE);
08126 if (!key) {
08127 ast_log(LOG_NOTICE, "Unable to find private key '%s'\n", keyn);
08128 } else {
08129 if (ast_sign(key, (char*)challenge, sig)) {
08130 ast_log(LOG_NOTICE, "Unable to sign challenge with key\n");
08131 res = -1;
08132 } else {
08133 iax_ie_append_str(ied, IAX_IE_RSA_RESULT, sig);
08134 res = 0;
08135 }
08136 }
08137 }
08138 }
08139
08140 if (res && !ast_strlen_zero(secret)) {
08141 if ((authmethods & IAX_AUTH_MD5) && !ast_strlen_zero(challenge)) {
08142 struct MD5Context md5;
08143 unsigned char digest[16];
08144 char digres[128];
08145 MD5Init(&md5);
08146 MD5Update(&md5, (unsigned char *)challenge, strlen(challenge));
08147 MD5Update(&md5, (unsigned char *)secret, strlen(secret));
08148 MD5Final(digest, &md5);
08149
08150 for (x=0;x<16;x++)
08151 sprintf(digres + (x << 1), "%2.2x", digest[x]);
08152 if (pvt) {
08153 build_encryption_keys(digest, pvt);
08154 }
08155 iax_ie_append_str(ied, IAX_IE_MD5_RESULT, digres);
08156 res = 0;
08157 } else if (authmethods & IAX_AUTH_PLAINTEXT) {
08158 iax_ie_append_str(ied, IAX_IE_PASSWORD, secret);
08159 res = 0;
08160 } else
08161 ast_log(LOG_NOTICE, "No way to send secret to peer '%s' (their methods: %d)\n", ast_inet_ntoa(sin->sin_addr), authmethods);
08162 }
08163 return res;
08164 }
08165
08166
08167
08168
08169
08170 static int authenticate_reply(struct chan_iax2_pvt *p, struct sockaddr_in *sin, struct iax_ies *ies, const char *override, const char *okey)
08171 {
08172 struct iax2_peer *peer = NULL;
08173
08174 int res = -1;
08175 int authmethods = 0;
08176 struct iax_ie_data ied;
08177 uint16_t callno = p->callno;
08178
08179 memset(&ied, 0, sizeof(ied));
08180
08181 if (ies->username)
08182 ast_string_field_set(p, username, ies->username);
08183 if (ies->challenge)
08184 ast_string_field_set(p, challenge, ies->challenge);
08185 if (ies->authmethods)
08186 authmethods = ies->authmethods;
08187 if (authmethods & IAX_AUTH_MD5)
08188 merge_encryption(p, ies->encmethods);
08189 else
08190 p->encmethods = 0;
08191
08192
08193 if (!ast_strlen_zero(override) || !ast_strlen_zero(okey)) {
08194
08195 res = authenticate(p->challenge, override, okey, authmethods, &ied, sin, p);
08196 } else {
08197 struct ao2_iterator i = ao2_iterator_init(peers, 0);
08198 while ((peer = ao2_iterator_next(&i))) {
08199 struct sockaddr_in peer_addr;
08200
08201 ast_sockaddr_to_sin(&peer->addr, &peer_addr);
08202
08203 if ((ast_strlen_zero(p->peer) || !strcmp(p->peer, peer->name))
08204
08205 && (ast_strlen_zero(peer->username) || (!strcmp(peer->username, p->username)))
08206
08207 && (!peer_addr.sin_addr.s_addr || ((sin->sin_addr.s_addr & peer->mask.s_addr) == (peer_addr.sin_addr.s_addr & peer->mask.s_addr)))
08208
08209 ) {
08210 res = authenticate(p->challenge, peer->secret, peer->outkey, authmethods, &ied, sin, p);
08211 if (!res) {
08212 peer_unref(peer);
08213 break;
08214 }
08215 }
08216 peer_unref(peer);
08217 }
08218 ao2_iterator_destroy(&i);
08219 if (!peer) {
08220
08221
08222 const char *peer_name = ast_strdupa(p->peer);
08223 ast_mutex_unlock(&iaxsl[callno]);
08224 if ((peer = realtime_peer(peer_name, NULL))) {
08225 ast_mutex_lock(&iaxsl[callno]);
08226 if (!(p = iaxs[callno])) {
08227 peer_unref(peer);
08228 return -1;
08229 }
08230 res = authenticate(p->challenge, peer->secret,peer->outkey, authmethods, &ied, sin, p);
08231 peer_unref(peer);
08232 }
08233 if (!peer) {
08234 ast_mutex_lock(&iaxsl[callno]);
08235 if (!(p = iaxs[callno]))
08236 return -1;
08237 }
08238 }
08239 }
08240
08241 if (ies->encmethods) {
08242 ast_set_flag64(p, IAX_ENCRYPTED | IAX_KEYPOPULATED);
08243 } else if (ast_test_flag64(iaxs[callno], IAX_FORCE_ENCRYPT)) {
08244 ast_log(LOG_NOTICE, "Call initiated without encryption while forceencryption=yes option is set\n");
08245 return -1;
08246 }
08247 if (!res) {
08248 struct ast_datastore *variablestore;
08249 struct ast_variable *var, *prev = NULL;
08250 AST_LIST_HEAD(, ast_var_t) *varlist;
08251 varlist = ast_calloc(1, sizeof(*varlist));
08252 variablestore = ast_datastore_alloc(&iax2_variable_datastore_info, NULL);
08253 if (variablestore && varlist && p->owner) {
08254 variablestore->data = varlist;
08255 variablestore->inheritance = DATASTORE_INHERIT_FOREVER;
08256 AST_LIST_HEAD_INIT(varlist);
08257 for (var = ies->vars; var; var = var->next) {
08258 struct ast_var_t *newvar = ast_var_assign(var->name, var->value);
08259 if (prev)
08260 ast_free(prev);
08261 prev = var;
08262 if (!newvar) {
08263
08264 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
08265 } else {
08266 AST_LIST_INSERT_TAIL(varlist, newvar, entries);
08267 }
08268 }
08269 if (prev)
08270 ast_free(prev);
08271 ies->vars = NULL;
08272 ast_channel_datastore_add(p->owner, variablestore);
08273 } else {
08274 if (p->owner)
08275 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
08276 if (variablestore)
08277 ast_datastore_free(variablestore);
08278 if (varlist)
08279 ast_free(varlist);
08280 }
08281 }
08282
08283 if (!res)
08284 res = send_command(p, AST_FRAME_IAX, IAX_COMMAND_AUTHREP, 0, ied.buf, ied.pos, -1);
08285 return res;
08286 }
08287
08288 static int iax2_do_register(struct iax2_registry *reg);
08289
08290 static void __iax2_do_register_s(const void *data)
08291 {
08292 struct iax2_registry *reg = (struct iax2_registry *)data;
08293 reg->expire = -1;
08294 iax2_do_register(reg);
08295 }
08296
08297 static int iax2_do_register_s(const void *data)
08298 {
08299 #ifdef SCHED_MULTITHREADED
08300 if (schedule_action(__iax2_do_register_s, data))
08301 #endif
08302 __iax2_do_register_s(data);
08303 return 0;
08304 }
08305
08306 static int try_transfer(struct chan_iax2_pvt *pvt, struct iax_ies *ies)
08307 {
08308 int newcall = 0;
08309 char newip[256];
08310 struct iax_ie_data ied;
08311 struct sockaddr_in new = { 0, };
08312
08313 memset(&ied, 0, sizeof(ied));
08314 if (ies->apparent_addr)
08315 memmove(&new, ies->apparent_addr, sizeof(new));
08316 if (ies->callno)
08317 newcall = ies->callno;
08318 if (!newcall || !new.sin_addr.s_addr || !new.sin_port) {
08319 ast_log(LOG_WARNING, "Invalid transfer request\n");
08320 return -1;
08321 }
08322 pvt->transfercallno = newcall;
08323 memcpy(&pvt->transfer, &new, sizeof(pvt->transfer));
08324 inet_aton(newip, &pvt->transfer.sin_addr);
08325 pvt->transfer.sin_family = AF_INET;
08326 pvt->transferid = ies->transferid;
08327
08328
08329 if (pvt->transferring == TRANSFER_NONE) {
08330 store_by_transfercallno(pvt);
08331 }
08332 pvt->transferring = TRANSFER_BEGIN;
08333
08334 if (ies->transferid)
08335 iax_ie_append_int(&ied, IAX_IE_TRANSFERID, ies->transferid);
08336 send_command_transfer(pvt, AST_FRAME_IAX, IAX_COMMAND_TXCNT, 0, ied.buf, ied.pos);
08337 return 0;
08338 }
08339
08340 static int complete_dpreply(struct chan_iax2_pvt *pvt, struct iax_ies *ies)
08341 {
08342 char exten[256] = "";
08343 int status = CACHE_FLAG_UNKNOWN, expiry = iaxdefaultdpcache, x, matchmore = 0;
08344 struct iax2_dpcache *dp = NULL;
08345
08346 if (ies->called_number)
08347 ast_copy_string(exten, ies->called_number, sizeof(exten));
08348
08349 if (ies->dpstatus & IAX_DPSTATUS_EXISTS)
08350 status = CACHE_FLAG_EXISTS;
08351 else if (ies->dpstatus & IAX_DPSTATUS_CANEXIST)
08352 status = CACHE_FLAG_CANEXIST;
08353 else if (ies->dpstatus & IAX_DPSTATUS_NONEXISTENT)
08354 status = CACHE_FLAG_NONEXISTENT;
08355
08356 if (ies->refresh)
08357 expiry = ies->refresh;
08358 if (ies->dpstatus & IAX_DPSTATUS_MATCHMORE)
08359 matchmore = CACHE_FLAG_MATCHMORE;
08360
08361 AST_LIST_LOCK(&dpcache);
08362 AST_LIST_TRAVERSE_SAFE_BEGIN(&dpcache, dp, peer_list) {
08363 if (strcmp(dp->exten, exten))
08364 continue;
08365 AST_LIST_REMOVE_CURRENT(peer_list);
08366 dp->callno = 0;
08367 dp->expiry.tv_sec = dp->orig.tv_sec + expiry;
08368 if (dp->flags & CACHE_FLAG_PENDING) {
08369 dp->flags &= ~CACHE_FLAG_PENDING;
08370 dp->flags |= status;
08371 dp->flags |= matchmore;
08372 }
08373
08374 for (x = 0; x < ARRAY_LEN(dp->waiters); x++) {
08375 if (dp->waiters[x] > -1) {
08376 if (write(dp->waiters[x], "asdf", 4) < 0) {
08377 }
08378 }
08379 }
08380 }
08381 AST_LIST_TRAVERSE_SAFE_END;
08382 AST_LIST_UNLOCK(&dpcache);
08383
08384 return 0;
08385 }
08386
08387 static int complete_transfer(int callno, struct iax_ies *ies)
08388 {
08389 int peercallno = 0;
08390 struct chan_iax2_pvt *pvt = iaxs[callno];
08391 struct iax_frame *cur;
08392 jb_frame frame;
08393
08394 if (ies->callno)
08395 peercallno = ies->callno;
08396
08397 if (peercallno < 1) {
08398 ast_log(LOG_WARNING, "Invalid transfer request\n");
08399 return -1;
08400 }
08401 remove_by_transfercallno(pvt);
08402
08403
08404
08405 peercnt_remove_by_addr(&pvt->addr);
08406 peercnt_add(&pvt->transfer);
08407
08408 memcpy(&pvt->addr, &pvt->transfer, sizeof(pvt->addr));
08409 memset(&pvt->transfer, 0, sizeof(pvt->transfer));
08410
08411 pvt->oseqno = 0;
08412 pvt->rseqno = 0;
08413 pvt->iseqno = 0;
08414 pvt->aseqno = 0;
08415
08416 if (pvt->peercallno) {
08417 remove_by_peercallno(pvt);
08418 }
08419 pvt->peercallno = peercallno;
08420
08421 store_by_peercallno(pvt);
08422 pvt->transferring = TRANSFER_NONE;
08423 pvt->svoiceformat = -1;
08424 pvt->voiceformat = 0;
08425 pvt->svideoformat = -1;
08426 pvt->videoformat = 0;
08427 pvt->transfercallno = 0;
08428 memset(&pvt->rxcore, 0, sizeof(pvt->rxcore));
08429 memset(&pvt->offset, 0, sizeof(pvt->offset));
08430
08431 while(jb_getall(pvt->jb,&frame) == JB_OK)
08432 iax2_frame_free(frame.data);
08433 jb_reset(pvt->jb);
08434 pvt->lag = 0;
08435 pvt->last = 0;
08436 pvt->lastsent = 0;
08437 pvt->nextpred = 0;
08438 pvt->pingtime = DEFAULT_RETRY_TIME;
08439 AST_LIST_TRAVERSE(&frame_queue[callno], cur, list) {
08440
08441
08442
08443 cur->retries = -1;
08444 }
08445 return 0;
08446 }
08447
08448
08449 static int iax2_ack_registry(struct iax_ies *ies, struct sockaddr_in *sin, int callno)
08450 {
08451 struct iax2_registry *reg;
08452
08453 char peer[256] = "";
08454 char msgstatus[60];
08455 int refresh = 60;
08456 char ourip[256] = "<Unspecified>";
08457 struct sockaddr_in oldus;
08458 struct sockaddr_in us;
08459 int oldmsgs;
08460 struct sockaddr_in reg_addr;
08461
08462 memset(&us, 0, sizeof(us));
08463 if (ies->apparent_addr) {
08464 memmove(&us, ies->apparent_addr, sizeof(us));
08465 }
08466 if (ies->username) {
08467 ast_copy_string(peer, ies->username, sizeof(peer));
08468 }
08469 if (ies->refresh) {
08470 refresh = ies->refresh;
08471 }
08472 if (ies->calling_number) {
08473
08474 }
08475 reg = iaxs[callno]->reg;
08476 if (!reg) {
08477 ast_log(LOG_WARNING, "Registry acknowledge on unknown registry '%s'\n", peer);
08478 return -1;
08479 }
08480 memcpy(&oldus, ®->us, sizeof(oldus));
08481 oldmsgs = reg->messages;
08482 ast_sockaddr_to_sin(®->addr, ®_addr);
08483 if (inaddrcmp(®_addr, sin)) {
08484 ast_log(LOG_WARNING, "Received unsolicited registry ack from '%s'\n", ast_inet_ntoa(sin->sin_addr));
08485 return -1;
08486 }
08487 memcpy(®->us, &us, sizeof(reg->us));
08488 if (ies->msgcount >= 0) {
08489 reg->messages = ies->msgcount & 0xffff;
08490 }
08491
08492
08493
08494 reg->refresh = refresh;
08495 reg->expire = iax2_sched_replace(reg->expire, sched,
08496 (5 * reg->refresh / 6) * 1000, iax2_do_register_s, reg);
08497 if (inaddrcmp(&oldus, ®->us) || (reg->messages != oldmsgs)) {
08498 if (reg->messages > 255) {
08499 snprintf(msgstatus, sizeof(msgstatus), " with %d new and %d old messages waiting", reg->messages & 0xff, reg->messages >> 8);
08500 } else if (reg->messages > 1) {
08501 snprintf(msgstatus, sizeof(msgstatus), " with %d new messages waiting", reg->messages);
08502 } else if (reg->messages > 0) {
08503 ast_copy_string(msgstatus, " with 1 new message waiting", sizeof(msgstatus));
08504 } else {
08505 ast_copy_string(msgstatus, " with no messages waiting", sizeof(msgstatus));
08506 }
08507 snprintf(ourip, sizeof(ourip), "%s:%d", ast_inet_ntoa(reg->us.sin_addr), ntohs(reg->us.sin_port));
08508 ast_verb(3, "Registered IAX2 to '%s', who sees us as %s%s\n", ast_inet_ntoa(sin->sin_addr), ourip, msgstatus);
08509 manager_event(EVENT_FLAG_SYSTEM, "Registry", "ChannelType: IAX2\r\nDomain: %s\r\nStatus: Registered\r\n", ast_inet_ntoa(sin->sin_addr));
08510 }
08511 reg->regstate = REG_STATE_REGISTERED;
08512 return 0;
08513 }
08514
08515 static int iax2_append_register(const char *hostname, const char *username,
08516 const char *secret, const char *porta)
08517 {
08518 struct iax2_registry *reg;
08519
08520 if (!(reg = ast_calloc(1, sizeof(*reg))))
08521 return -1;
08522
08523 reg->addr.ss.ss_family = AF_INET;
08524 if (ast_dnsmgr_lookup(hostname, ®->addr, ®->dnsmgr, srvlookup ? "_iax._udp" : NULL) < 0) {
08525 ast_free(reg);
08526 return -1;
08527 }
08528
08529 ast_copy_string(reg->username, username, sizeof(reg->username));
08530
08531 if (secret)
08532 ast_copy_string(reg->secret, secret, sizeof(reg->secret));
08533
08534 reg->expire = -1;
08535 reg->refresh = IAX_DEFAULT_REG_EXPIRE;
08536 ast_sockaddr_set_port(®->addr, porta ? atoi(porta) : IAX_DEFAULT_PORTNO);
08537
08538 AST_LIST_LOCK(®istrations);
08539 AST_LIST_INSERT_HEAD(®istrations, reg, entry);
08540 AST_LIST_UNLOCK(®istrations);
08541
08542 return 0;
08543 }
08544
08545 static int iax2_register(const char *value, int lineno)
08546 {
08547 char copy[256];
08548 char *username, *hostname, *secret;
08549 char *porta;
08550 char *stringp=NULL;
08551
08552 if (!value)
08553 return -1;
08554
08555 ast_copy_string(copy, value, sizeof(copy));
08556 stringp = copy;
08557 username = strsep(&stringp, "@");
08558 hostname = strsep(&stringp, "@");
08559
08560 if (!hostname) {
08561 ast_log(LOG_WARNING, "Format for registration is user[:secret]@host[:port] at line %d\n", lineno);
08562 return -1;
08563 }
08564
08565 stringp = username;
08566 username = strsep(&stringp, ":");
08567 secret = strsep(&stringp, ":");
08568 stringp = hostname;
08569 hostname = strsep(&stringp, ":");
08570 porta = strsep(&stringp, ":");
08571
08572 if (porta && !atoi(porta)) {
08573 ast_log(LOG_WARNING, "%s is not a valid port number at line %d\n", porta, lineno);
08574 return -1;
08575 }
08576
08577 return iax2_append_register(hostname, username, secret, porta);
08578 }
08579
08580
08581 static void register_peer_exten(struct iax2_peer *peer, int onoff)
08582 {
08583 char multi[256];
08584 char *stringp, *ext;
08585 if (!ast_strlen_zero(regcontext)) {
08586 ast_copy_string(multi, S_OR(peer->regexten, peer->name), sizeof(multi));
08587 stringp = multi;
08588 while((ext = strsep(&stringp, "&"))) {
08589 if (onoff) {
08590 if (!ast_exists_extension(NULL, regcontext, ext, 1, NULL))
08591 ast_add_extension(regcontext, 1, ext, 1, NULL, NULL,
08592 "Noop", ast_strdup(peer->name), ast_free_ptr, "IAX2");
08593 } else
08594 ast_context_remove_extension(regcontext, ext, 1, NULL);
08595 }
08596 }
08597 }
08598 static void prune_peers(void);
08599
08600 static void unlink_peer(struct iax2_peer *peer)
08601 {
08602 if (peer->expire > -1) {
08603 if (!ast_sched_thread_del(sched, peer->expire)) {
08604 peer->expire = -1;
08605 peer_unref(peer);
08606 }
08607 }
08608
08609 if (peer->pokeexpire > -1) {
08610 if (!ast_sched_thread_del(sched, peer->pokeexpire)) {
08611 peer->pokeexpire = -1;
08612 peer_unref(peer);
08613 }
08614 }
08615
08616 ao2_unlink(peers, peer);
08617 }
08618
08619 static void __expire_registry(const void *data)
08620 {
08621 struct iax2_peer *peer = (struct iax2_peer *) data;
08622
08623 if (!peer)
08624 return;
08625 if (peer->expire == -1) {
08626
08627 return;
08628 }
08629
08630 peer->expire = -1;
08631
08632 ast_debug(1, "Expiring registration for peer '%s'\n", peer->name);
08633 if (ast_test_flag64((&globalflags), IAX_RTUPDATE) && (ast_test_flag64(peer, IAX_TEMPONLY|IAX_RTCACHEFRIENDS)))
08634 realtime_update_peer(peer->name, &peer->addr, 0);
08635 manager_event(EVENT_FLAG_SYSTEM, "PeerStatus", "ChannelType: IAX2\r\nPeer: IAX2/%s\r\nPeerStatus: Unregistered\r\nCause: Expired\r\n", peer->name);
08636
08637 peercnt_modify(0, 0, &peer->addr);
08638
08639 memset(&peer->addr, 0, sizeof(peer->addr));
08640
08641 peer->expiry = min_reg_expire;
08642 if (!ast_test_flag64(peer, IAX_TEMPONLY))
08643 ast_db_del("IAX/Registry", peer->name);
08644 register_peer_exten(peer, 0);
08645 ast_devstate_changed(AST_DEVICE_UNAVAILABLE, "IAX2/%s", peer->name);
08646 if (iax2_regfunk)
08647 iax2_regfunk(peer->name, 0);
08648
08649 if (ast_test_flag64(peer, IAX_RTAUTOCLEAR))
08650 unlink_peer(peer);
08651
08652 peer_unref(peer);
08653 }
08654
08655 static int expire_registry(const void *data)
08656 {
08657 #ifdef SCHED_MULTITHREADED
08658 if (schedule_action(__expire_registry, data))
08659 #endif
08660 __expire_registry(data);
08661 return 0;
08662 }
08663
08664 static int iax2_poke_peer(struct iax2_peer *peer, int heldcall);
08665
08666 static void reg_source_db(struct iax2_peer *p)
08667 {
08668 char data[80];
08669 char *expiry;
08670
08671 if (ast_test_flag64(p, IAX_TEMPONLY) || ast_db_get("IAX/Registry", p->name, data, sizeof(data))) {
08672 return;
08673 }
08674
08675 expiry = strrchr(data, ':');
08676 if (!expiry) {
08677 ast_log(LOG_NOTICE, "IAX/Registry astdb entry missing expiry: '%s'\n", data);
08678 return;
08679 }
08680 *expiry++ = '\0';
08681
08682 if (!ast_sockaddr_parse(&p->addr, data, PARSE_PORT_REQUIRE)) {
08683 ast_log(LOG_NOTICE, "IAX/Registry astdb host:port invalid - '%s'\n", data);
08684 return;
08685 }
08686
08687 p->expiry = atoi(expiry);
08688
08689 ast_verb(3, "Seeding '%s' at %s for %d\n", p->name,
08690 ast_sockaddr_stringify(&p->addr), p->expiry);
08691
08692 iax2_poke_peer(p, 0);
08693 if (p->expire > -1) {
08694 if (!ast_sched_thread_del(sched, p->expire)) {
08695 p->expire = -1;
08696 peer_unref(p);
08697 }
08698 }
08699
08700 ast_devstate_changed(AST_DEVICE_UNKNOWN, "IAX2/%s", p->name);
08701
08702 p->expire = iax2_sched_add(sched, (p->expiry + 10) * 1000, expire_registry, peer_ref(p));
08703 if (p->expire == -1) {
08704 peer_unref(p);
08705 }
08706
08707 if (iax2_regfunk) {
08708 iax2_regfunk(p->name, 1);
08709 }
08710
08711 register_peer_exten(p, 1);
08712 }
08713
08714
08715
08716
08717
08718
08719
08720 static int update_registry(struct sockaddr_in *sin, int callno, char *devtype, int fd, unsigned short refresh)
08721 {
08722
08723 struct iax_ie_data ied = {
08724 .pos = 0,
08725 };
08726 struct iax2_peer *p;
08727 int msgcount;
08728 char data[80];
08729 int version;
08730 const char *peer_name;
08731 int res = -1;
08732 struct ast_sockaddr sockaddr;
08733
08734 ast_sockaddr_from_sin(&sockaddr, sin);
08735
08736 peer_name = ast_strdupa(iaxs[callno]->peer);
08737
08738
08739 ast_mutex_unlock(&iaxsl[callno]);
08740 if (!(p = find_peer(peer_name, 1))) {
08741 ast_mutex_lock(&iaxsl[callno]);
08742 ast_log(LOG_WARNING, "No such peer '%s'\n", peer_name);
08743 return -1;
08744 }
08745 ast_mutex_lock(&iaxsl[callno]);
08746 if (!iaxs[callno])
08747 goto return_unref;
08748
08749 if (ast_test_flag64((&globalflags), IAX_RTUPDATE) && (ast_test_flag64(p, IAX_TEMPONLY|IAX_RTCACHEFRIENDS))) {
08750 if (sin->sin_addr.s_addr) {
08751 time_t nowtime;
08752 time(&nowtime);
08753 realtime_update_peer(peer_name, &sockaddr, nowtime);
08754 } else {
08755 realtime_update_peer(peer_name, &sockaddr, 0);
08756 }
08757 }
08758
08759 if (ast_sockaddr_cmp(&p->addr, &sockaddr)) {
08760 if (iax2_regfunk) {
08761 iax2_regfunk(p->name, 1);
08762 }
08763
08764
08765 peercnt_modify(0, 0, &p->addr);
08766
08767
08768 ast_sockaddr_from_sin(&p->addr, sin);
08769
08770 snprintf(data, sizeof(data), "%s:%d:%d", ast_inet_ntoa(sin->sin_addr), ntohs(sin->sin_port), p->expiry);
08771 if (!ast_test_flag64(p, IAX_TEMPONLY) && sin->sin_addr.s_addr) {
08772 ast_db_put("IAX/Registry", p->name, data);
08773 ast_verb(3, "Registered IAX2 '%s' (%s) at %s:%d\n", p->name,
08774 ast_test_flag(&iaxs[callno]->state, IAX_STATE_AUTHENTICATED) ? "AUTHENTICATED" : "UNAUTHENTICATED", ast_inet_ntoa(sin->sin_addr), ntohs(sin->sin_port));
08775 manager_event(EVENT_FLAG_SYSTEM, "PeerStatus", "ChannelType: IAX2\r\nPeer: IAX2/%s\r\nPeerStatus: Registered\r\n", p->name);
08776 register_peer_exten(p, 1);
08777 ast_devstate_changed(AST_DEVICE_UNKNOWN, "IAX2/%s", p->name);
08778 } else if (!ast_test_flag64(p, IAX_TEMPONLY)) {
08779 ast_verb(3, "Unregistered IAX2 '%s' (%s)\n", p->name,
08780 ast_test_flag(&iaxs[callno]->state, IAX_STATE_AUTHENTICATED) ? "AUTHENTICATED" : "UNAUTHENTICATED");
08781 manager_event(EVENT_FLAG_SYSTEM, "PeerStatus", "ChannelType: IAX2\r\nPeer: IAX2/%s\r\nPeerStatus: Unregistered\r\n", p->name);
08782 register_peer_exten(p, 0);
08783 ast_db_del("IAX/Registry", p->name);
08784 ast_devstate_changed(AST_DEVICE_UNAVAILABLE, "IAX2/%s", p->name);
08785 }
08786
08787
08788 iax2_poke_peer(p, callno);
08789 }
08790
08791
08792 if (p->maxcallno) {
08793 peercnt_modify(1, p->maxcallno, &p->addr);
08794 }
08795
08796
08797 if (!iaxs[callno]) {
08798 res = -1;
08799 goto return_unref;
08800 }
08801
08802
08803 p->sockfd = fd;
08804
08805 if (p->expire > -1) {
08806 if (!ast_sched_thread_del(sched, p->expire)) {
08807 p->expire = -1;
08808 peer_unref(p);
08809 }
08810 }
08811
08812 if (!refresh)
08813 refresh = min_reg_expire;
08814 if (refresh > max_reg_expire) {
08815 ast_log(LOG_NOTICE, "Restricting registration for peer '%s' to %d seconds (requested %d)\n",
08816 p->name, max_reg_expire, refresh);
08817 p->expiry = max_reg_expire;
08818 } else if (refresh < min_reg_expire) {
08819 ast_log(LOG_NOTICE, "Restricting registration for peer '%s' to %d seconds (requested %d)\n",
08820 p->name, min_reg_expire, refresh);
08821 p->expiry = min_reg_expire;
08822 } else {
08823 p->expiry = refresh;
08824 }
08825 if (p->expiry && sin->sin_addr.s_addr) {
08826 p->expire = iax2_sched_add(sched, (p->expiry + 10) * 1000, expire_registry, peer_ref(p));
08827 if (p->expire == -1)
08828 peer_unref(p);
08829 }
08830 iax_ie_append_str(&ied, IAX_IE_USERNAME, p->name);
08831 iax_ie_append_int(&ied, IAX_IE_DATETIME, iax2_datetime(p->zonetag));
08832 if (sin->sin_addr.s_addr) {
08833 struct sockaddr_in peer_addr;
08834
08835 ast_sockaddr_to_sin(&p->addr, &peer_addr);
08836
08837 iax_ie_append_short(&ied, IAX_IE_REFRESH, p->expiry);
08838 iax_ie_append_addr(&ied, IAX_IE_APPARENT_ADDR, &peer_addr);
08839 if (!ast_strlen_zero(p->mailbox)) {
08840 struct ast_event *event;
08841 int new, old;
08842 char *mailbox, *context;
08843
08844 context = mailbox = ast_strdupa(p->mailbox);
08845 strsep(&context, "@");
08846 if (ast_strlen_zero(context))
08847 context = "default";
08848
08849 event = ast_event_get_cached(AST_EVENT_MWI,
08850 AST_EVENT_IE_MAILBOX, AST_EVENT_IE_PLTYPE_STR, mailbox,
08851 AST_EVENT_IE_CONTEXT, AST_EVENT_IE_PLTYPE_STR, context,
08852 AST_EVENT_IE_END);
08853 if (event) {
08854 new = ast_event_get_ie_uint(event, AST_EVENT_IE_NEWMSGS);
08855 old = ast_event_get_ie_uint(event, AST_EVENT_IE_OLDMSGS);
08856 ast_event_destroy(event);
08857 } else {
08858 ast_app_inboxcount(p->mailbox, &new, &old);
08859 }
08860
08861 if (new > 255) {
08862 new = 255;
08863 }
08864 if (old > 255) {
08865 old = 255;
08866 }
08867 msgcount = (old << 8) | new;
08868
08869 iax_ie_append_short(&ied, IAX_IE_MSGCOUNT, msgcount);
08870 }
08871 if (ast_test_flag64(p, IAX_HASCALLERID)) {
08872 iax_ie_append_str(&ied, IAX_IE_CALLING_NUMBER, p->cid_num);
08873 iax_ie_append_str(&ied, IAX_IE_CALLING_NAME, p->cid_name);
08874 }
08875 }
08876 version = iax_check_version(devtype);
08877 if (version)
08878 iax_ie_append_short(&ied, IAX_IE_FIRMWAREVER, version);
08879
08880 res = 0;
08881
08882 return_unref:
08883 peer_unref(p);
08884
08885 return res ? res : send_command_final(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_REGACK, 0, ied.buf, ied.pos, -1);
08886 }
08887
08888 static int registry_authrequest(int callno)
08889 {
08890 struct iax_ie_data ied;
08891 struct iax2_peer *p;
08892 char challenge[10];
08893 const char *peer_name;
08894 int sentauthmethod;
08895
08896 peer_name = ast_strdupa(iaxs[callno]->peer);
08897
08898
08899 ast_mutex_unlock(&iaxsl[callno]);
08900 if ((p = find_peer(peer_name, 1))) {
08901 last_authmethod = p->authmethods;
08902 }
08903
08904 ast_mutex_lock(&iaxsl[callno]);
08905 if (!iaxs[callno])
08906 goto return_unref;
08907
08908 memset(&ied, 0, sizeof(ied));
08909
08910
08911
08912
08913
08914
08915 sentauthmethod = p ? p->authmethods : last_authmethod ? last_authmethod : (IAX_AUTH_MD5 | IAX_AUTH_PLAINTEXT);
08916 if (!p) {
08917 iaxs[callno]->authmethods = sentauthmethod;
08918 }
08919 iax_ie_append_short(&ied, IAX_IE_AUTHMETHODS, sentauthmethod);
08920 if (sentauthmethod & (IAX_AUTH_RSA | IAX_AUTH_MD5)) {
08921
08922 snprintf(challenge, sizeof(challenge), "%d", (int)ast_random());
08923 ast_string_field_set(iaxs[callno], challenge, challenge);
08924 iax_ie_append_str(&ied, IAX_IE_CHALLENGE, iaxs[callno]->challenge);
08925 }
08926 iax_ie_append_str(&ied, IAX_IE_USERNAME, peer_name);
08927
08928 return_unref:
08929 if (p) {
08930 peer_unref(p);
08931 }
08932
08933 return iaxs[callno] ? send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_REGAUTH, 0, ied.buf, ied.pos, -1) : -1;
08934 }
08935
08936 static int registry_rerequest(struct iax_ies *ies, int callno, struct sockaddr_in *sin)
08937 {
08938 struct iax2_registry *reg;
08939
08940 struct iax_ie_data ied;
08941 char peer[256] = "";
08942 char challenge[256] = "";
08943 int res;
08944 int authmethods = 0;
08945 if (ies->authmethods)
08946 authmethods = ies->authmethods;
08947 if (ies->username)
08948 ast_copy_string(peer, ies->username, sizeof(peer));
08949 if (ies->challenge)
08950 ast_copy_string(challenge, ies->challenge, sizeof(challenge));
08951 memset(&ied, 0, sizeof(ied));
08952 reg = iaxs[callno]->reg;
08953 if (reg) {
08954 struct sockaddr_in reg_addr;
08955
08956 ast_sockaddr_to_sin(®->addr, ®_addr);
08957
08958 if (inaddrcmp(®_addr, sin)) {
08959 ast_log(LOG_WARNING, "Received unsolicited registry authenticate request from '%s'\n", ast_inet_ntoa(sin->sin_addr));
08960 return -1;
08961 }
08962 if (ast_strlen_zero(reg->secret)) {
08963 ast_log(LOG_NOTICE, "No secret associated with peer '%s'\n", reg->username);
08964 reg->regstate = REG_STATE_NOAUTH;
08965 return -1;
08966 }
08967 iax_ie_append_str(&ied, IAX_IE_USERNAME, reg->username);
08968 iax_ie_append_short(&ied, IAX_IE_REFRESH, reg->refresh);
08969 if (reg->secret[0] == '[') {
08970 char tmpkey[256];
08971 ast_copy_string(tmpkey, reg->secret + 1, sizeof(tmpkey));
08972 tmpkey[strlen(tmpkey) - 1] = '\0';
08973 res = authenticate(challenge, NULL, tmpkey, authmethods, &ied, sin, NULL);
08974 } else
08975 res = authenticate(challenge, reg->secret, NULL, authmethods, &ied, sin, NULL);
08976 if (!res) {
08977 reg->regstate = REG_STATE_AUTHSENT;
08978 add_empty_calltoken_ie(iaxs[callno], &ied);
08979 return send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_REGREQ, 0, ied.buf, ied.pos, -1);
08980 } else
08981 return -1;
08982 ast_log(LOG_WARNING, "Registry acknowledge on unknown registery '%s'\n", peer);
08983 } else
08984 ast_log(LOG_NOTICE, "Can't reregister without a reg\n");
08985 return -1;
08986 }
08987
08988 static void stop_stuff(int callno)
08989 {
08990 iax2_destroy_helper(iaxs[callno]);
08991 }
08992
08993 static void __auth_reject(const void *nothing)
08994 {
08995
08996 int callno = (int)(long)(nothing);
08997 struct iax_ie_data ied;
08998 ast_mutex_lock(&iaxsl[callno]);
08999 if (iaxs[callno]) {
09000 memset(&ied, 0, sizeof(ied));
09001 if (iaxs[callno]->authfail == IAX_COMMAND_REGREJ) {
09002 iax_ie_append_str(&ied, IAX_IE_CAUSE, "Registration Refused");
09003 iax_ie_append_byte(&ied, IAX_IE_CAUSECODE, AST_CAUSE_FACILITY_REJECTED);
09004 } else if (iaxs[callno]->authfail == IAX_COMMAND_REJECT) {
09005 iax_ie_append_str(&ied, IAX_IE_CAUSE, "No authority found");
09006 iax_ie_append_byte(&ied, IAX_IE_CAUSECODE, AST_CAUSE_FACILITY_NOT_SUBSCRIBED);
09007 }
09008 send_command_final(iaxs[callno], AST_FRAME_IAX, iaxs[callno]->authfail, 0, ied.buf, ied.pos, -1);
09009 }
09010 ast_mutex_unlock(&iaxsl[callno]);
09011 }
09012
09013 static int auth_reject(const void *data)
09014 {
09015 int callno = (int)(long)(data);
09016 ast_mutex_lock(&iaxsl[callno]);
09017 if (iaxs[callno])
09018 iaxs[callno]->authid = -1;
09019 ast_mutex_unlock(&iaxsl[callno]);
09020 #ifdef SCHED_MULTITHREADED
09021 if (schedule_action(__auth_reject, data))
09022 #endif
09023 __auth_reject(data);
09024 return 0;
09025 }
09026
09027 static int auth_fail(int callno, int failcode)
09028 {
09029
09030
09031 if (iaxs[callno]) {
09032 iaxs[callno]->authfail = failcode;
09033 if (delayreject) {
09034 iaxs[callno]->authid = iax2_sched_replace(iaxs[callno]->authid,
09035 sched, 1000, auth_reject, (void *)(long)callno);
09036 } else
09037 auth_reject((void *)(long)callno);
09038 }
09039 return 0;
09040 }
09041
09042 static void __auto_hangup(const void *nothing)
09043 {
09044
09045 int callno = (int)(long)(nothing);
09046 struct iax_ie_data ied;
09047 ast_mutex_lock(&iaxsl[callno]);
09048 if (iaxs[callno]) {
09049 memset(&ied, 0, sizeof(ied));
09050 iax_ie_append_str(&ied, IAX_IE_CAUSE, "Timeout");
09051 iax_ie_append_byte(&ied, IAX_IE_CAUSECODE, AST_CAUSE_NO_USER_RESPONSE);
09052 send_command_final(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_HANGUP, 0, ied.buf, ied.pos, -1);
09053 }
09054 ast_mutex_unlock(&iaxsl[callno]);
09055 }
09056
09057 static int auto_hangup(const void *data)
09058 {
09059 int callno = (int)(long)(data);
09060 ast_mutex_lock(&iaxsl[callno]);
09061 if (iaxs[callno]) {
09062 iaxs[callno]->autoid = -1;
09063 }
09064 ast_mutex_unlock(&iaxsl[callno]);
09065 #ifdef SCHED_MULTITHREADED
09066 if (schedule_action(__auto_hangup, data))
09067 #endif
09068 __auto_hangup(data);
09069 return 0;
09070 }
09071
09072 static void iax2_dprequest(struct iax2_dpcache *dp, int callno)
09073 {
09074 struct iax_ie_data ied;
09075
09076 iaxs[callno]->autoid = iax2_sched_replace(iaxs[callno]->autoid,
09077 sched, 30000, auto_hangup, (void *)(long)callno);
09078 memset(&ied, 0, sizeof(ied));
09079 iax_ie_append_str(&ied, IAX_IE_CALLED_NUMBER, dp->exten);
09080 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_DPREQ, 0, ied.buf, ied.pos, -1);
09081 dp->flags |= CACHE_FLAG_TRANSMITTED;
09082 }
09083
09084 static int iax2_vnak(int callno)
09085 {
09086 return send_command_immediate(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_VNAK, 0, NULL, 0, iaxs[callno]->iseqno);
09087 }
09088
09089 static void vnak_retransmit(int callno, int last)
09090 {
09091 struct iax_frame *f;
09092
09093 AST_LIST_TRAVERSE(&frame_queue[callno], f, list) {
09094
09095 if (((unsigned char) (f->oseqno - last) < 128) &&
09096 (f->retries >= 0)) {
09097 send_packet(f);
09098 }
09099 }
09100 }
09101
09102 static void __iax2_poke_peer_s(const void *data)
09103 {
09104 struct iax2_peer *peer = (struct iax2_peer *)data;
09105 iax2_poke_peer(peer, 0);
09106 peer_unref(peer);
09107 }
09108
09109 static int iax2_poke_peer_s(const void *data)
09110 {
09111 struct iax2_peer *peer = (struct iax2_peer *)data;
09112 peer->pokeexpire = -1;
09113 #ifdef SCHED_MULTITHREADED
09114 if (schedule_action(__iax2_poke_peer_s, data))
09115 #endif
09116 __iax2_poke_peer_s(data);
09117 return 0;
09118 }
09119
09120 static int send_trunk(struct iax2_trunk_peer *tpeer, struct timeval *now)
09121 {
09122 int res = 0;
09123 struct iax_frame *fr;
09124 struct ast_iax2_meta_hdr *meta;
09125 struct ast_iax2_meta_trunk_hdr *mth;
09126 int calls = 0;
09127
09128
09129 fr = (struct iax_frame *)tpeer->trunkdata;
09130
09131 meta = (struct ast_iax2_meta_hdr *)fr->afdata;
09132 mth = (struct ast_iax2_meta_trunk_hdr *)meta->data;
09133 if (tpeer->trunkdatalen) {
09134
09135 meta->zeros = 0;
09136 meta->metacmd = IAX_META_TRUNK;
09137 if (ast_test_flag64(&globalflags, IAX_TRUNKTIMESTAMPS))
09138 meta->cmddata = IAX_META_TRUNK_MINI;
09139 else
09140 meta->cmddata = IAX_META_TRUNK_SUPERMINI;
09141 mth->ts = htonl(calc_txpeerstamp(tpeer, trunkfreq, now));
09142
09143 fr->direction = DIRECTION_OUTGRESS;
09144 fr->retrans = -1;
09145 fr->transfer = 0;
09146
09147 fr->data = fr->afdata;
09148 fr->datalen = tpeer->trunkdatalen + sizeof(struct ast_iax2_meta_hdr) + sizeof(struct ast_iax2_meta_trunk_hdr);
09149 res = transmit_trunk(fr, &tpeer->addr, tpeer->sockfd);
09150 calls = tpeer->calls;
09151 #if 0
09152 ast_debug(1, "Trunking %d call chunks in %d bytes to %s:%d, ts=%d\n", calls, fr->datalen, ast_inet_ntoa(tpeer->addr.sin_addr), ntohs(tpeer->addr.sin_port), ntohl(mth->ts));
09153 #endif
09154
09155 tpeer->trunkdatalen = 0;
09156 tpeer->calls = 0;
09157 }
09158 if (res < 0)
09159 return res;
09160 return calls;
09161 }
09162
09163 static inline int iax2_trunk_expired(struct iax2_trunk_peer *tpeer, struct timeval *now)
09164 {
09165
09166 if (now->tv_sec > tpeer->trunkact.tv_sec + 5)
09167 return 1;
09168 return 0;
09169 }
09170
09171 static int timing_read(int *id, int fd, short events, void *cbdata)
09172 {
09173 int res, processed = 0, totalcalls = 0;
09174 struct iax2_trunk_peer *tpeer = NULL, *drop = NULL;
09175 struct timeval now = ast_tvnow();
09176
09177 if (iaxtrunkdebug)
09178 ast_verbose("Beginning trunk processing. Trunk queue ceiling is %d bytes per host\n", trunkmaxsize);
09179
09180 if (timer) {
09181 ast_timer_ack(timer, 1);
09182 }
09183
09184
09185 AST_LIST_LOCK(&tpeers);
09186 AST_LIST_TRAVERSE_SAFE_BEGIN(&tpeers, tpeer, list) {
09187 processed++;
09188 res = 0;
09189 ast_mutex_lock(&tpeer->lock);
09190
09191
09192 if (!drop && iax2_trunk_expired(tpeer, &now)) {
09193
09194
09195 AST_LIST_REMOVE_CURRENT(list);
09196 drop = tpeer;
09197 } else {
09198 res = send_trunk(tpeer, &now);
09199 trunk_timed++;
09200 if (iaxtrunkdebug)
09201 ast_verbose(" - Trunk peer (%s:%d) has %d call chunk%s in transit, %d bytes backloged and has hit a high water mark of %d bytes\n", ast_inet_ntoa(tpeer->addr.sin_addr), ntohs(tpeer->addr.sin_port), res, (res != 1) ? "s" : "", tpeer->trunkdatalen, tpeer->trunkdataalloc);
09202 }
09203 totalcalls += res;
09204 res = 0;
09205 ast_mutex_unlock(&tpeer->lock);
09206 }
09207 AST_LIST_TRAVERSE_SAFE_END;
09208 AST_LIST_UNLOCK(&tpeers);
09209
09210 if (drop) {
09211 ast_mutex_lock(&drop->lock);
09212
09213
09214 ast_debug(1, "Dropping unused iax2 trunk peer '%s:%d'\n", ast_inet_ntoa(drop->addr.sin_addr), ntohs(drop->addr.sin_port));
09215 if (drop->trunkdata) {
09216 ast_free(drop->trunkdata);
09217 drop->trunkdata = NULL;
09218 }
09219 ast_mutex_unlock(&drop->lock);
09220 ast_mutex_destroy(&drop->lock);
09221 ast_free(drop);
09222
09223 }
09224
09225 if (iaxtrunkdebug)
09226 ast_verbose("Ending trunk processing with %d peers and %d call chunks processed\n", processed, totalcalls);
09227 iaxtrunkdebug = 0;
09228
09229 return 1;
09230 }
09231
09232 struct dpreq_data {
09233 int callno;
09234 char context[AST_MAX_EXTENSION];
09235 char callednum[AST_MAX_EXTENSION];
09236 char *callerid;
09237 };
09238
09239 static void dp_lookup(int callno, const char *context, const char *callednum, const char *callerid, int skiplock)
09240 {
09241 unsigned short dpstatus = 0;
09242 struct iax_ie_data ied1;
09243 int mm;
09244
09245 memset(&ied1, 0, sizeof(ied1));
09246 mm = ast_matchmore_extension(NULL, context, callednum, 1, callerid);
09247
09248 if (ast_parking_ext_valid(callednum, NULL, context) || ast_exists_extension(NULL, context, callednum, 1, callerid)) {
09249 dpstatus = IAX_DPSTATUS_EXISTS;
09250 } else if (ast_canmatch_extension(NULL, context, callednum, 1, callerid)) {
09251 dpstatus = IAX_DPSTATUS_CANEXIST;
09252 } else {
09253 dpstatus = IAX_DPSTATUS_NONEXISTENT;
09254 }
09255 if (ast_ignore_pattern(context, callednum))
09256 dpstatus |= IAX_DPSTATUS_IGNOREPAT;
09257 if (mm)
09258 dpstatus |= IAX_DPSTATUS_MATCHMORE;
09259 if (!skiplock)
09260 ast_mutex_lock(&iaxsl[callno]);
09261 if (iaxs[callno]) {
09262 iax_ie_append_str(&ied1, IAX_IE_CALLED_NUMBER, callednum);
09263 iax_ie_append_short(&ied1, IAX_IE_DPSTATUS, dpstatus);
09264 iax_ie_append_short(&ied1, IAX_IE_REFRESH, iaxdefaultdpcache);
09265 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_DPREP, 0, ied1.buf, ied1.pos, -1);
09266 }
09267 if (!skiplock)
09268 ast_mutex_unlock(&iaxsl[callno]);
09269 }
09270
09271 static void *dp_lookup_thread(void *data)
09272 {
09273
09274 struct dpreq_data *dpr = data;
09275 dp_lookup(dpr->callno, dpr->context, dpr->callednum, dpr->callerid, 0);
09276 if (dpr->callerid)
09277 ast_free(dpr->callerid);
09278 ast_free(dpr);
09279 return NULL;
09280 }
09281
09282 static void spawn_dp_lookup(int callno, const char *context, const char *callednum, const char *callerid)
09283 {
09284 pthread_t newthread;
09285 struct dpreq_data *dpr;
09286
09287 if (!(dpr = ast_calloc(1, sizeof(*dpr))))
09288 return;
09289
09290 dpr->callno = callno;
09291 ast_copy_string(dpr->context, context, sizeof(dpr->context));
09292 ast_copy_string(dpr->callednum, callednum, sizeof(dpr->callednum));
09293 if (callerid)
09294 dpr->callerid = ast_strdup(callerid);
09295 if (ast_pthread_create_detached(&newthread, NULL, dp_lookup_thread, dpr)) {
09296 ast_log(LOG_WARNING, "Unable to start lookup thread!\n");
09297 }
09298 }
09299
09300 struct iax_dual {
09301 struct ast_channel *chan1;
09302 struct ast_channel *chan2;
09303 char *park_exten;
09304 char *park_context;
09305 };
09306
09307 static void *iax_park_thread(void *stuff)
09308 {
09309 struct iax_dual *d;
09310 int res;
09311 int ext = 0;
09312
09313 d = stuff;
09314
09315 ast_debug(4, "IAX Park: Transferer channel %s, Transferee %s\n",
09316 d->chan2->name, d->chan1->name);
09317
09318 res = ast_park_call_exten(d->chan1, d->chan2, d->park_exten, d->park_context, 0, &ext);
09319 if (res) {
09320
09321 ast_hangup(d->chan1);
09322 } else {
09323 ast_log(LOG_NOTICE, "Parked on extension '%d'\n", ext);
09324 }
09325 ast_hangup(d->chan2);
09326
09327 ast_free(d->park_exten);
09328 ast_free(d->park_context);
09329 ast_free(d);
09330 return NULL;
09331 }
09332
09333
09334 static int iax_park(struct ast_channel *chan1, struct ast_channel *chan2, const char *park_exten, const char *park_context)
09335 {
09336 struct iax_dual *d;
09337 struct ast_channel *chan1m, *chan2m;
09338 pthread_t th;
09339
09340 chan1m = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, chan2->accountcode, chan1->exten, chan1->context, chan1->linkedid, chan1->amaflags, "Parking/%s", chan1->name);
09341 chan2m = ast_channel_alloc(0, AST_STATE_DOWN, 0, 0, chan2->accountcode, chan2->exten, chan2->context, chan2->linkedid, chan2->amaflags, "IAXPeer/%s", chan2->name);
09342 d = ast_calloc(1, sizeof(*d));
09343 if (!chan1m || !chan2m || !d) {
09344 if (chan1m) {
09345 ast_hangup(chan1m);
09346 }
09347 if (chan2m) {
09348 ast_hangup(chan2m);
09349 }
09350 ast_free(d);
09351 return -1;
09352 }
09353 d->park_exten = ast_strdup(park_exten);
09354 d->park_context = ast_strdup(park_context);
09355 if (!d->park_exten || !d->park_context) {
09356 ast_hangup(chan1m);
09357 ast_hangup(chan2m);
09358 ast_free(d->park_exten);
09359 ast_free(d->park_context);
09360 ast_free(d);
09361 return -1;
09362 }
09363
09364
09365 chan1m->readformat = chan1->readformat;
09366 chan1m->writeformat = chan1->writeformat;
09367
09368
09369 if (ast_channel_masquerade(chan1m, chan1)) {
09370 ast_hangup(chan1m);
09371 ast_hangup(chan2m);
09372 ast_free(d->park_exten);
09373 ast_free(d->park_context);
09374 ast_free(d);
09375 return -1;
09376 }
09377
09378
09379 ast_copy_string(chan1m->context, chan1->context, sizeof(chan1m->context));
09380 ast_copy_string(chan1m->exten, chan1->exten, sizeof(chan1m->exten));
09381 chan1m->priority = chan1->priority;
09382
09383 ast_do_masquerade(chan1m);
09384
09385
09386
09387
09388
09389 chan2m->readformat = chan2->readformat;
09390 chan2m->writeformat = chan2->writeformat;
09391 ast_string_field_set(chan2m, parkinglot, chan2->parkinglot);
09392
09393
09394 if (ast_channel_masquerade(chan2m, chan2)) {
09395 ast_hangup(chan1m);
09396 ast_hangup(chan2m);
09397 ast_free(d->park_exten);
09398 ast_free(d->park_context);
09399 ast_free(d);
09400 return -1;
09401 }
09402
09403
09404 ast_copy_string(chan2m->context, chan2->context, sizeof(chan2m->context));
09405 ast_copy_string(chan2m->exten, chan2->exten, sizeof(chan2m->exten));
09406 chan2m->priority = chan2->priority;
09407
09408 ast_do_masquerade(chan2m);
09409
09410 d->chan1 = chan1m;
09411 d->chan2 = chan2m;
09412 if (ast_pthread_create_detached_background(&th, NULL, iax_park_thread, d) < 0) {
09413
09414 ast_hangup(chan1m);
09415 ast_hangup(chan2m);
09416 ast_free(d->park_exten);
09417 ast_free(d->park_context);
09418 ast_free(d);
09419 return -1;
09420 }
09421 return 0;
09422 }
09423
09424 static int check_provisioning(struct sockaddr_in *sin, int sockfd, char *si, unsigned int ver)
09425 {
09426 unsigned int ourver;
09427 char rsi[80];
09428 snprintf(rsi, sizeof(rsi), "si-%s", si);
09429 if (iax_provision_version(&ourver, rsi, 1))
09430 return 0;
09431 ast_debug(1, "Service identifier '%s', we think '%08x', they think '%08x'\n", si, ourver, ver);
09432 if (ourver != ver)
09433 iax2_provision(sin, sockfd, NULL, rsi, 1);
09434 return 0;
09435 }
09436
09437 static void construct_rr(struct chan_iax2_pvt *pvt, struct iax_ie_data *iep)
09438 {
09439 jb_info stats;
09440 jb_getinfo(pvt->jb, &stats);
09441
09442 memset(iep, 0, sizeof(*iep));
09443
09444 iax_ie_append_int(iep,IAX_IE_RR_JITTER, stats.jitter);
09445 if(stats.frames_in == 0) stats.frames_in = 1;
09446 iax_ie_append_int(iep,IAX_IE_RR_LOSS, ((0xff & (stats.losspct/1000)) << 24 | (stats.frames_lost & 0x00ffffff)));
09447 iax_ie_append_int(iep,IAX_IE_RR_PKTS, stats.frames_in);
09448 iax_ie_append_short(iep,IAX_IE_RR_DELAY, stats.current - stats.min);
09449 iax_ie_append_int(iep,IAX_IE_RR_DROPPED, stats.frames_dropped);
09450 iax_ie_append_int(iep,IAX_IE_RR_OOO, stats.frames_ooo);
09451 }
09452
09453 static void save_rr(struct iax_frame *fr, struct iax_ies *ies)
09454 {
09455 iaxs[fr->callno]->remote_rr.jitter = ies->rr_jitter;
09456 iaxs[fr->callno]->remote_rr.losspct = ies->rr_loss >> 24;
09457 iaxs[fr->callno]->remote_rr.losscnt = ies->rr_loss & 0xffffff;
09458 iaxs[fr->callno]->remote_rr.packets = ies->rr_pkts;
09459 iaxs[fr->callno]->remote_rr.delay = ies->rr_delay;
09460 iaxs[fr->callno]->remote_rr.dropped = ies->rr_dropped;
09461 iaxs[fr->callno]->remote_rr.ooo = ies->rr_ooo;
09462 }
09463
09464 static void save_osptoken(struct iax_frame *fr, struct iax_ies *ies)
09465 {
09466 int i;
09467 unsigned int length, offset = 0;
09468 char full_osptoken[IAX_MAX_OSPBUFF_SIZE];
09469
09470 for (i = 0; i < IAX_MAX_OSPBLOCK_NUM; i++) {
09471 length = ies->ospblocklength[i];
09472 if (length != 0) {
09473 if (length > IAX_MAX_OSPBLOCK_SIZE) {
09474
09475 offset = 0;
09476 break;
09477 } else {
09478 memcpy(full_osptoken + offset, ies->osptokenblock[i], length);
09479 offset += length;
09480 }
09481 } else {
09482 break;
09483 }
09484 }
09485 *(full_osptoken + offset) = '\0';
09486 if (strlen(full_osptoken) != offset) {
09487
09488 *full_osptoken = '\0';
09489 }
09490
09491 ast_string_field_set(iaxs[fr->callno], osptoken, full_osptoken);
09492 }
09493
09494 static void log_jitterstats(unsigned short callno)
09495 {
09496 int localjitter = -1, localdelay = 0, locallost = -1, locallosspct = -1, localdropped = 0, localooo = -1, localpackets = -1;
09497 jb_info jbinfo;
09498
09499 ast_mutex_lock(&iaxsl[callno]);
09500 if (iaxs[callno] && iaxs[callno]->owner && iaxs[callno]->owner->name) {
09501 if(ast_test_flag64(iaxs[callno], IAX_USEJITTERBUF)) {
09502 jb_getinfo(iaxs[callno]->jb, &jbinfo);
09503 localjitter = jbinfo.jitter;
09504 localdelay = jbinfo.current - jbinfo.min;
09505 locallost = jbinfo.frames_lost;
09506 locallosspct = jbinfo.losspct/1000;
09507 localdropped = jbinfo.frames_dropped;
09508 localooo = jbinfo.frames_ooo;
09509 localpackets = jbinfo.frames_in;
09510 }
09511 ast_debug(3, "JB STATS:%s ping=%d ljitterms=%d ljbdelayms=%d ltotlost=%d lrecentlosspct=%d ldropped=%d looo=%d lrecvd=%d rjitterms=%d rjbdelayms=%d rtotlost=%d rrecentlosspct=%d rdropped=%d rooo=%d rrecvd=%d\n",
09512 iaxs[callno]->owner->name,
09513 iaxs[callno]->pingtime,
09514 localjitter,
09515 localdelay,
09516 locallost,
09517 locallosspct,
09518 localdropped,
09519 localooo,
09520 localpackets,
09521 iaxs[callno]->remote_rr.jitter,
09522 iaxs[callno]->remote_rr.delay,
09523 iaxs[callno]->remote_rr.losscnt,
09524 iaxs[callno]->remote_rr.losspct/1000,
09525 iaxs[callno]->remote_rr.dropped,
09526 iaxs[callno]->remote_rr.ooo,
09527 iaxs[callno]->remote_rr.packets);
09528 manager_event(EVENT_FLAG_REPORTING, "JitterBufStats", "Owner: %s\r\nPing: %d\r\nLocalJitter: %d\r\nLocalJBDelay: %d\r\nLocalTotalLost: %d\r\nLocalLossPercent: %d\r\nLocalDropped: %d\r\nLocalooo: %d\r\nLocalReceived: %d\r\nRemoteJitter: %d\r\nRemoteJBDelay: %d\r\nRemoteTotalLost: %d\r\nRemoteLossPercent: %d\r\nRemoteDropped: %d\r\nRemoteooo: %d\r\nRemoteReceived: %d\r\n",
09529 iaxs[callno]->owner->name,
09530 iaxs[callno]->pingtime,
09531 localjitter,
09532 localdelay,
09533 locallost,
09534 locallosspct,
09535 localdropped,
09536 localooo,
09537 localpackets,
09538 iaxs[callno]->remote_rr.jitter,
09539 iaxs[callno]->remote_rr.delay,
09540 iaxs[callno]->remote_rr.losscnt,
09541 iaxs[callno]->remote_rr.losspct/1000,
09542 iaxs[callno]->remote_rr.dropped,
09543 iaxs[callno]->remote_rr.ooo,
09544 iaxs[callno]->remote_rr.packets);
09545 }
09546 ast_mutex_unlock(&iaxsl[callno]);
09547 }
09548
09549 static int socket_process(struct iax2_thread *thread);
09550
09551
09552
09553
09554 static void handle_deferred_full_frames(struct iax2_thread *thread)
09555 {
09556 struct iax2_pkt_buf *pkt_buf;
09557
09558 ast_mutex_lock(&thread->lock);
09559
09560 while ((pkt_buf = AST_LIST_REMOVE_HEAD(&thread->full_frames, entry))) {
09561 ast_mutex_unlock(&thread->lock);
09562
09563 thread->buf = pkt_buf->buf;
09564 thread->buf_len = pkt_buf->len;
09565 thread->buf_size = pkt_buf->len + 1;
09566
09567 socket_process(thread);
09568
09569 thread->buf = NULL;
09570 ast_free(pkt_buf);
09571
09572 ast_mutex_lock(&thread->lock);
09573 }
09574
09575 ast_mutex_unlock(&thread->lock);
09576 }
09577
09578
09579
09580
09581
09582
09583
09584 static void defer_full_frame(struct iax2_thread *from_here, struct iax2_thread *to_here)
09585 {
09586 struct iax2_pkt_buf *pkt_buf, *cur_pkt_buf;
09587 struct ast_iax2_full_hdr *fh, *cur_fh;
09588
09589 if (!(pkt_buf = ast_calloc(1, sizeof(*pkt_buf) + from_here->buf_len)))
09590 return;
09591
09592 pkt_buf->len = from_here->buf_len;
09593 memcpy(pkt_buf->buf, from_here->buf, pkt_buf->len);
09594
09595 fh = (struct ast_iax2_full_hdr *) pkt_buf->buf;
09596 ast_mutex_lock(&to_here->lock);
09597 AST_LIST_TRAVERSE_SAFE_BEGIN(&to_here->full_frames, cur_pkt_buf, entry) {
09598 cur_fh = (struct ast_iax2_full_hdr *) cur_pkt_buf->buf;
09599 if (fh->oseqno < cur_fh->oseqno) {
09600 AST_LIST_INSERT_BEFORE_CURRENT(pkt_buf, entry);
09601 break;
09602 }
09603 }
09604 AST_LIST_TRAVERSE_SAFE_END
09605
09606 if (!cur_pkt_buf)
09607 AST_LIST_INSERT_TAIL(&to_here->full_frames, pkt_buf, entry);
09608
09609 ast_mutex_unlock(&to_here->lock);
09610 }
09611
09612 static int socket_read(int *id, int fd, short events, void *cbdata)
09613 {
09614 struct iax2_thread *thread;
09615 socklen_t len;
09616 time_t t;
09617 static time_t last_errtime = 0;
09618 struct ast_iax2_full_hdr *fh;
09619
09620 if (!(thread = find_idle_thread())) {
09621 time(&t);
09622 if (t != last_errtime)
09623 ast_debug(1, "Out of idle IAX2 threads for I/O, pausing!\n");
09624 last_errtime = t;
09625 usleep(1);
09626 return 1;
09627 }
09628
09629 len = sizeof(thread->iosin);
09630 thread->iofd = fd;
09631 thread->buf_len = recvfrom(fd, thread->readbuf, sizeof(thread->readbuf), 0, (struct sockaddr *) &thread->iosin, &len);
09632 thread->buf_size = sizeof(thread->readbuf);
09633 thread->buf = thread->readbuf;
09634 if (thread->buf_len < 0) {
09635 if (errno != ECONNREFUSED && errno != EAGAIN)
09636 ast_log(LOG_WARNING, "Error: %s\n", strerror(errno));
09637 handle_error();
09638 thread->iostate = IAX_IOSTATE_IDLE;
09639 signal_condition(&thread->lock, &thread->cond);
09640 return 1;
09641 }
09642 if (test_losspct && ((100.0 * ast_random() / (RAND_MAX + 1.0)) < test_losspct)) {
09643 thread->iostate = IAX_IOSTATE_IDLE;
09644 signal_condition(&thread->lock, &thread->cond);
09645 return 1;
09646 }
09647
09648
09649
09650
09651 fh = (struct ast_iax2_full_hdr *) thread->buf;
09652 if (ntohs(fh->scallno) & IAX_FLAG_FULL) {
09653 struct iax2_thread *cur = NULL;
09654 uint16_t callno = ntohs(fh->scallno) & ~IAX_FLAG_FULL;
09655
09656 AST_LIST_LOCK(&active_list);
09657 AST_LIST_TRAVERSE(&active_list, cur, list) {
09658 if ((cur->ffinfo.callno == callno) &&
09659 !inaddrcmp(&cur->ffinfo.sin, &thread->iosin))
09660 break;
09661 }
09662 if (cur) {
09663
09664
09665 defer_full_frame(thread, cur);
09666 AST_LIST_UNLOCK(&active_list);
09667 thread->iostate = IAX_IOSTATE_IDLE;
09668 signal_condition(&thread->lock, &thread->cond);
09669 return 1;
09670 } else {
09671
09672 thread->ffinfo.callno = callno;
09673 memcpy(&thread->ffinfo.sin, &thread->iosin, sizeof(thread->ffinfo.sin));
09674 thread->ffinfo.type = fh->type;
09675 thread->ffinfo.csub = fh->csub;
09676 AST_LIST_INSERT_HEAD(&active_list, thread, list);
09677 }
09678 AST_LIST_UNLOCK(&active_list);
09679 }
09680
09681
09682 thread->iostate = IAX_IOSTATE_READY;
09683 #ifdef DEBUG_SCHED_MULTITHREAD
09684 ast_copy_string(thread->curfunc, "socket_process", sizeof(thread->curfunc));
09685 #endif
09686 signal_condition(&thread->lock, &thread->cond);
09687
09688 return 1;
09689 }
09690
09691 static int socket_process_meta(int packet_len, struct ast_iax2_meta_hdr *meta, struct sockaddr_in *sin, int sockfd,
09692 struct iax_frame *fr)
09693 {
09694 unsigned char metatype;
09695 struct ast_iax2_meta_trunk_mini *mtm;
09696 struct ast_iax2_meta_trunk_hdr *mth;
09697 struct ast_iax2_meta_trunk_entry *mte;
09698 struct iax2_trunk_peer *tpeer;
09699 unsigned int ts;
09700 void *ptr;
09701 struct timeval rxtrunktime;
09702 struct ast_frame f = { 0, };
09703
09704 if (packet_len < sizeof(*meta)) {
09705 ast_log(LOG_WARNING, "Rejecting packet from '%s.%d' that is flagged as a meta frame but is too short\n",
09706 ast_inet_ntoa(sin->sin_addr), ntohs(sin->sin_port));
09707 return 1;
09708 }
09709
09710 if (meta->metacmd != IAX_META_TRUNK)
09711 return 1;
09712
09713 if (packet_len < (sizeof(*meta) + sizeof(*mth))) {
09714 ast_log(LOG_WARNING, "midget meta trunk packet received (%d of %d min)\n", packet_len,
09715 (int) (sizeof(*meta) + sizeof(*mth)));
09716 return 1;
09717 }
09718 mth = (struct ast_iax2_meta_trunk_hdr *)(meta->data);
09719 ts = ntohl(mth->ts);
09720 metatype = meta->cmddata;
09721 packet_len -= (sizeof(*meta) + sizeof(*mth));
09722 ptr = mth->data;
09723 tpeer = find_tpeer(sin, sockfd);
09724 if (!tpeer) {
09725 ast_log(LOG_WARNING, "Unable to accept trunked packet from '%s:%d': No matching peer\n",
09726 ast_inet_ntoa(sin->sin_addr), ntohs(sin->sin_port));
09727 return 1;
09728 }
09729 tpeer->trunkact = ast_tvnow();
09730 if (!ts || ast_tvzero(tpeer->rxtrunktime))
09731 tpeer->rxtrunktime = tpeer->trunkact;
09732 rxtrunktime = tpeer->rxtrunktime;
09733 ast_mutex_unlock(&tpeer->lock);
09734 while (packet_len >= sizeof(*mte)) {
09735
09736 unsigned short callno, trunked_ts, len;
09737
09738 if (metatype == IAX_META_TRUNK_MINI) {
09739 mtm = (struct ast_iax2_meta_trunk_mini *) ptr;
09740 ptr += sizeof(*mtm);
09741 packet_len -= sizeof(*mtm);
09742 len = ntohs(mtm->len);
09743 callno = ntohs(mtm->mini.callno);
09744 trunked_ts = ntohs(mtm->mini.ts);
09745 } else if (metatype == IAX_META_TRUNK_SUPERMINI) {
09746 mte = (struct ast_iax2_meta_trunk_entry *)ptr;
09747 ptr += sizeof(*mte);
09748 packet_len -= sizeof(*mte);
09749 len = ntohs(mte->len);
09750 callno = ntohs(mte->callno);
09751 trunked_ts = 0;
09752 } else {
09753 ast_log(LOG_WARNING, "Unknown meta trunk cmd from '%s:%d': dropping\n", ast_inet_ntoa(sin->sin_addr), ntohs(sin->sin_port));
09754 break;
09755 }
09756
09757 if (len > packet_len)
09758 break;
09759 fr->callno = find_callno_locked(callno & ~IAX_FLAG_FULL, 0, sin, NEW_PREVENT, sockfd, 0);
09760 if (!fr->callno)
09761 continue;
09762
09763
09764
09765
09766 memset(&f, 0, sizeof(f));
09767 f.frametype = AST_FRAME_VOICE;
09768 if (!iaxs[fr->callno]) {
09769
09770 } else if (iaxs[fr->callno]->voiceformat == 0) {
09771 ast_log(LOG_WARNING, "Received trunked frame before first full voice frame\n");
09772 iax2_vnak(fr->callno);
09773 } else {
09774 f.subclass.codec = iaxs[fr->callno]->voiceformat;
09775 f.datalen = len;
09776 if (f.datalen >= 0) {
09777 if (f.datalen)
09778 f.data.ptr = ptr;
09779 else
09780 f.data.ptr = NULL;
09781 if (trunked_ts)
09782 fr->ts = (iaxs[fr->callno]->last & 0xFFFF0000L) | (trunked_ts & 0xffff);
09783 else
09784 fr->ts = fix_peerts(&rxtrunktime, fr->callno, ts);
09785
09786 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED)) {
09787 struct iax_frame *duped_fr;
09788
09789
09790 f.src = "IAX2";
09791 f.mallocd = 0;
09792 f.offset = 0;
09793 if (f.datalen && (f.frametype == AST_FRAME_VOICE))
09794 f.samples = ast_codec_get_samples(&f);
09795 else
09796 f.samples = 0;
09797 fr->outoforder = 0;
09798 iax_frame_wrap(fr, &f);
09799 duped_fr = iaxfrdup2(fr);
09800 if (duped_fr)
09801 schedule_delivery(duped_fr, 1, 1, &fr->ts);
09802 if (iaxs[fr->callno] && iaxs[fr->callno]->last < fr->ts)
09803 iaxs[fr->callno]->last = fr->ts;
09804 }
09805 } else {
09806 ast_log(LOG_WARNING, "Datalen < 0?\n");
09807 }
09808 }
09809 ast_mutex_unlock(&iaxsl[fr->callno]);
09810 ptr += len;
09811 packet_len -= len;
09812 }
09813
09814 return 1;
09815 }
09816
09817 static int acf_iaxvar_read(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
09818 {
09819 struct ast_datastore *variablestore = ast_channel_datastore_find(chan, &iax2_variable_datastore_info, NULL);
09820 AST_LIST_HEAD(, ast_var_t) *varlist;
09821 struct ast_var_t *var;
09822
09823 if (!variablestore) {
09824 *buf = '\0';
09825 return 0;
09826 }
09827 varlist = variablestore->data;
09828
09829 AST_LIST_LOCK(varlist);
09830 AST_LIST_TRAVERSE(varlist, var, entries) {
09831 if (strcmp(var->name, data) == 0) {
09832 ast_copy_string(buf, var->value, len);
09833 break;
09834 }
09835 }
09836 AST_LIST_UNLOCK(varlist);
09837 return 0;
09838 }
09839
09840 static int acf_iaxvar_write(struct ast_channel *chan, const char *cmd, char *data, const char *value)
09841 {
09842 struct ast_datastore *variablestore = ast_channel_datastore_find(chan, &iax2_variable_datastore_info, NULL);
09843 AST_LIST_HEAD(, ast_var_t) *varlist;
09844 struct ast_var_t *var;
09845
09846 if (!variablestore) {
09847 variablestore = ast_datastore_alloc(&iax2_variable_datastore_info, NULL);
09848 if (!variablestore) {
09849 ast_log(LOG_ERROR, "Memory allocation error\n");
09850 return -1;
09851 }
09852 varlist = ast_calloc(1, sizeof(*varlist));
09853 if (!varlist) {
09854 ast_datastore_free(variablestore);
09855 ast_log(LOG_ERROR, "Unable to assign new variable '%s'\n", data);
09856 return -1;
09857 }
09858
09859 AST_LIST_HEAD_INIT(varlist);
09860 variablestore->data = varlist;
09861 variablestore->inheritance = DATASTORE_INHERIT_FOREVER;
09862 ast_channel_datastore_add(chan, variablestore);
09863 } else
09864 varlist = variablestore->data;
09865
09866 AST_LIST_LOCK(varlist);
09867 AST_LIST_TRAVERSE_SAFE_BEGIN(varlist, var, entries) {
09868 if (strcmp(var->name, data) == 0) {
09869 AST_LIST_REMOVE_CURRENT(entries);
09870 ast_var_delete(var);
09871 break;
09872 }
09873 }
09874 AST_LIST_TRAVERSE_SAFE_END;
09875 var = ast_var_assign(data, value);
09876 if (var)
09877 AST_LIST_INSERT_TAIL(varlist, var, entries);
09878 else
09879 ast_log(LOG_ERROR, "Unable to assign new variable '%s'\n", data);
09880 AST_LIST_UNLOCK(varlist);
09881 return 0;
09882 }
09883
09884 static struct ast_custom_function iaxvar_function = {
09885 .name = "IAXVAR",
09886 .read = acf_iaxvar_read,
09887 .write = acf_iaxvar_write,
09888 };
09889
09890 static void set_hangup_source_and_cause(int callno, unsigned char causecode)
09891 {
09892 iax2_lock_owner(callno);
09893 if (iaxs[callno] && iaxs[callno]->owner) {
09894 struct ast_channel *owner;
09895 const char *name;
09896
09897 owner = iaxs[callno]->owner;
09898 if (causecode) {
09899 owner->hangupcause = causecode;
09900 }
09901 name = ast_strdupa(owner->name);
09902 ast_channel_ref(owner);
09903 ast_channel_unlock(owner);
09904 ast_mutex_unlock(&iaxsl[callno]);
09905 ast_set_hangupsource(owner, name, 0);
09906 ast_channel_unref(owner);
09907 ast_mutex_lock(&iaxsl[callno]);
09908 }
09909 }
09910
09911 static int socket_process(struct iax2_thread *thread)
09912 {
09913 struct sockaddr_in sin;
09914 int res;
09915 int updatehistory=1;
09916 int new = NEW_PREVENT;
09917 int dcallno = 0;
09918 char decrypted = 0;
09919 struct ast_iax2_full_hdr *fh = (struct ast_iax2_full_hdr *)thread->buf;
09920 struct ast_iax2_mini_hdr *mh = (struct ast_iax2_mini_hdr *)thread->buf;
09921 struct ast_iax2_meta_hdr *meta = (struct ast_iax2_meta_hdr *)thread->buf;
09922 struct ast_iax2_video_hdr *vh = (struct ast_iax2_video_hdr *)thread->buf;
09923 struct iax_frame *fr;
09924 struct iax_frame *cur;
09925 struct ast_frame f = { 0, };
09926 struct ast_channel *c = NULL;
09927 struct iax2_dpcache *dp;
09928 struct iax2_peer *peer;
09929 struct iax_ies ies;
09930 struct iax_ie_data ied0, ied1;
09931 format_t format;
09932 int fd;
09933 int exists;
09934 int minivid = 0;
09935 char empty[32]="";
09936 struct iax_frame *duped_fr;
09937 char host_pref_buf[128];
09938 char caller_pref_buf[128];
09939 struct ast_codec_pref pref;
09940 char *using_prefs = "mine";
09941
09942
09943 fr = alloca(sizeof(*fr) + 4096);
09944 memset(fr, 0, sizeof(*fr));
09945 fr->afdatalen = 4096;
09946
09947
09948 res = thread->buf_len;
09949 fd = thread->iofd;
09950 memcpy(&sin, &thread->iosin, sizeof(sin));
09951
09952 if (res < sizeof(*mh)) {
09953 ast_log(LOG_WARNING, "midget packet received (%d of %d min)\n", res, (int) sizeof(*mh));
09954 return 1;
09955 }
09956 if ((vh->zeros == 0) && (ntohs(vh->callno) & 0x8000)) {
09957 if (res < sizeof(*vh)) {
09958 ast_log(LOG_WARNING, "Rejecting packet from '%s.%d' that is flagged as a video frame but is too short\n", ast_inet_ntoa(sin.sin_addr), ntohs(sin.sin_port));
09959 return 1;
09960 }
09961
09962
09963 fr->callno = find_callno(ntohs(vh->callno) & ~0x8000, dcallno, &sin, new, fd, 0);
09964 minivid = 1;
09965 } else if ((meta->zeros == 0) && !(ntohs(meta->metacmd) & 0x8000))
09966 return socket_process_meta(res, meta, &sin, fd, fr);
09967
09968 #ifdef DEBUG_SUPPORT
09969 if (res >= sizeof(*fh))
09970 iax_outputframe(NULL, fh, 1, &sin, res - sizeof(*fh));
09971 #endif
09972 if (ntohs(mh->callno) & IAX_FLAG_FULL) {
09973 if (res < sizeof(*fh)) {
09974 ast_log(LOG_WARNING, "Rejecting packet from '%s.%d' that is flagged as a full frame but is too short\n", ast_inet_ntoa(sin.sin_addr), ntohs(sin.sin_port));
09975 return 1;
09976 }
09977
09978
09979 dcallno = ntohs(fh->dcallno) & ~IAX_FLAG_RETRANS;
09980
09981
09982
09983
09984
09985
09986 if ((dcallno != 1) && (fr->callno = find_callno(ntohs(mh->callno) & ~IAX_FLAG_FULL, dcallno, &sin, NEW_PREVENT, fd, 1))) {
09987 ast_mutex_lock(&iaxsl[fr->callno]);
09988 if (iaxs[fr->callno] && ast_test_flag64(iaxs[fr->callno], IAX_ENCRYPTED)) {
09989 if (decrypt_frame(fr->callno, fh, &f, &res)) {
09990 ast_log(LOG_NOTICE, "Packet Decrypt Failed!\n");
09991 ast_mutex_unlock(&iaxsl[fr->callno]);
09992 return 1;
09993 }
09994 decrypted = 1;
09995 }
09996 ast_mutex_unlock(&iaxsl[fr->callno]);
09997 }
09998
09999
10000 f.frametype = fh->type;
10001 if (f.frametype == AST_FRAME_VIDEO) {
10002 f.subclass.codec = uncompress_subclass(fh->csub & ~0x40) | ((fh->csub >> 6) & 0x1);
10003 } else if (f.frametype == AST_FRAME_VOICE) {
10004 f.subclass.codec = uncompress_subclass(fh->csub);
10005 } else {
10006 f.subclass.integer = uncompress_subclass(fh->csub);
10007 }
10008
10009
10010 if (f.frametype == AST_FRAME_IAX && f.subclass.integer == IAX_COMMAND_POKE) {
10011
10012 send_apathetic_reply(1, ntohs(fh->scallno), &sin, IAX_COMMAND_PONG, ntohl(fh->ts), fh->iseqno + 1, fd, NULL);
10013 return 1;
10014 } else if (f.frametype == AST_FRAME_IAX && f.subclass.integer == IAX_COMMAND_ACK && dcallno == 1) {
10015
10016 return 1;
10017 }
10018
10019 f.datalen = res - sizeof(*fh);
10020 if (f.datalen) {
10021 if (f.frametype == AST_FRAME_IAX) {
10022 if (iax_parse_ies(&ies, thread->buf + sizeof(struct ast_iax2_full_hdr), f.datalen)) {
10023 ast_log(LOG_WARNING, "Undecodable frame received from '%s'\n", ast_inet_ntoa(sin.sin_addr));
10024 ast_variables_destroy(ies.vars);
10025 return 1;
10026 }
10027 f.data.ptr = NULL;
10028 f.datalen = 0;
10029 } else {
10030 f.data.ptr = thread->buf + sizeof(struct ast_iax2_full_hdr);
10031 memset(&ies, 0, sizeof(ies));
10032 }
10033 } else {
10034 if (f.frametype == AST_FRAME_IAX)
10035 f.data.ptr = NULL;
10036 else
10037 f.data.ptr = empty;
10038 memset(&ies, 0, sizeof(ies));
10039 }
10040
10041 if (!dcallno && iax2_allow_new(f.frametype, f.subclass.integer, 1)) {
10042
10043 if (handle_call_token(fh, &ies, &sin, fd)) {
10044 ast_variables_destroy(ies.vars);
10045 return 1;
10046 }
10047
10048 if (ies.calltoken && ies.calltokendata) {
10049
10050
10051
10052
10053 new = NEW_ALLOW_CALLTOKEN_VALIDATED;
10054 } else {
10055 new = NEW_ALLOW;
10056 }
10057 }
10058 } else {
10059
10060 f.frametype = AST_FRAME_NULL;
10061 f.subclass.integer = 0;
10062 memset(&ies, 0, sizeof(ies));
10063 }
10064
10065 if (!fr->callno) {
10066 int check_dcallno = 0;
10067
10068
10069
10070
10071
10072
10073
10074
10075
10076 if ((ntohs(mh->callno) & IAX_FLAG_FULL) && ((f.frametype == AST_FRAME_IAX) && (f.subclass.integer == IAX_COMMAND_ACK))) {
10077 check_dcallno = 1;
10078 }
10079
10080 if (!(fr->callno = find_callno(ntohs(mh->callno) & ~IAX_FLAG_FULL, dcallno, &sin, new, fd, check_dcallno))) {
10081 if (f.frametype == AST_FRAME_IAX && f.subclass.integer == IAX_COMMAND_NEW) {
10082 send_apathetic_reply(1, ntohs(fh->scallno), &sin, IAX_COMMAND_REJECT, ntohl(fh->ts), fh->iseqno + 1, fd, NULL);
10083 } else if (f.frametype == AST_FRAME_IAX && (f.subclass.integer == IAX_COMMAND_REGREQ || f.subclass.integer == IAX_COMMAND_REGREL)) {
10084 send_apathetic_reply(1, ntohs(fh->scallno), &sin, IAX_COMMAND_REGREJ, ntohl(fh->ts), fh->iseqno + 1, fd, NULL);
10085 }
10086 ast_variables_destroy(ies.vars);
10087 return 1;
10088 }
10089 }
10090
10091 if (fr->callno > 0)
10092 ast_mutex_lock(&iaxsl[fr->callno]);
10093
10094 if (!fr->callno || !iaxs[fr->callno]) {
10095
10096
10097 if (ntohs(mh->callno) & IAX_FLAG_FULL) {
10098
10099 if (((f.subclass.integer != IAX_COMMAND_INVAL) &&
10100 (f.subclass.integer != IAX_COMMAND_TXCNT) &&
10101 (f.subclass.integer != IAX_COMMAND_TXACC) &&
10102 (f.subclass.integer != IAX_COMMAND_FWDOWNL))||
10103 (f.frametype != AST_FRAME_IAX))
10104 raw_hangup(&sin, ntohs(fh->dcallno) & ~IAX_FLAG_RETRANS, ntohs(mh->callno) & ~IAX_FLAG_FULL,
10105 fd);
10106 }
10107 if (fr->callno > 0)
10108 ast_mutex_unlock(&iaxsl[fr->callno]);
10109 ast_variables_destroy(ies.vars);
10110 return 1;
10111 }
10112 if (ast_test_flag64(iaxs[fr->callno], IAX_ENCRYPTED) && !decrypted) {
10113 if (decrypt_frame(fr->callno, fh, &f, &res)) {
10114 ast_log(LOG_NOTICE, "Packet Decrypt Failed!\n");
10115 ast_variables_destroy(ies.vars);
10116 ast_mutex_unlock(&iaxsl[fr->callno]);
10117 return 1;
10118 }
10119 decrypted = 1;
10120 }
10121
10122 #ifdef DEBUG_SUPPORT
10123 if (decrypted) {
10124 iax_outputframe(NULL, fh, 3, &sin, res - sizeof(*fh));
10125 }
10126 #endif
10127
10128
10129
10130 iaxs[fr->callno]->frames_received++;
10131
10132 if (!inaddrcmp(&sin, &iaxs[fr->callno]->addr) && !minivid &&
10133 f.subclass.integer != IAX_COMMAND_TXCNT &&
10134 f.subclass.integer != IAX_COMMAND_TXACC) {
10135 unsigned short new_peercallno;
10136
10137 new_peercallno = (unsigned short) (ntohs(mh->callno) & ~IAX_FLAG_FULL);
10138 if (new_peercallno && new_peercallno != iaxs[fr->callno]->peercallno) {
10139 if (iaxs[fr->callno]->peercallno) {
10140 remove_by_peercallno(iaxs[fr->callno]);
10141 }
10142 iaxs[fr->callno]->peercallno = new_peercallno;
10143 store_by_peercallno(iaxs[fr->callno]);
10144 }
10145 }
10146 if (ntohs(mh->callno) & IAX_FLAG_FULL) {
10147 if (iaxdebug)
10148 ast_debug(1, "Received packet %d, (%d, %u)\n", fh->oseqno, f.frametype, f.subclass.integer);
10149
10150 fr->oseqno = fh->oseqno;
10151 fr->iseqno = fh->iseqno;
10152 fr->ts = ntohl(fh->ts);
10153 #ifdef IAXTESTS
10154 if (test_resync) {
10155 ast_debug(1, "Simulating frame ts resync, was %u now %u\n", fr->ts, fr->ts + test_resync);
10156 fr->ts += test_resync;
10157 }
10158 #endif
10159 #if 0
10160 if ( (ntohs(fh->dcallno) & IAX_FLAG_RETRANS) ||
10161 ( (f.frametype != AST_FRAME_VOICE) && ! (f.frametype == AST_FRAME_IAX &&
10162 (f.subclass == IAX_COMMAND_NEW ||
10163 f.subclass == IAX_COMMAND_AUTHREQ ||
10164 f.subclass == IAX_COMMAND_ACCEPT ||
10165 f.subclass == IAX_COMMAND_REJECT)) ) )
10166 #endif
10167 if ((ntohs(fh->dcallno) & IAX_FLAG_RETRANS) || (f.frametype != AST_FRAME_VOICE))
10168 updatehistory = 0;
10169 if ((iaxs[fr->callno]->iseqno != fr->oseqno) &&
10170 (iaxs[fr->callno]->iseqno ||
10171 ((f.subclass.integer != IAX_COMMAND_TXCNT) &&
10172 (f.subclass.integer != IAX_COMMAND_TXREADY) &&
10173 (f.subclass.integer != IAX_COMMAND_TXREL) &&
10174 (f.subclass.integer != IAX_COMMAND_UNQUELCH ) &&
10175 (f.subclass.integer != IAX_COMMAND_TXACC)) ||
10176 (f.frametype != AST_FRAME_IAX))) {
10177 if (
10178 ((f.subclass.integer != IAX_COMMAND_ACK) &&
10179 (f.subclass.integer != IAX_COMMAND_INVAL) &&
10180 (f.subclass.integer != IAX_COMMAND_TXCNT) &&
10181 (f.subclass.integer != IAX_COMMAND_TXREADY) &&
10182 (f.subclass.integer != IAX_COMMAND_TXREL) &&
10183 (f.subclass.integer != IAX_COMMAND_UNQUELCH ) &&
10184 (f.subclass.integer != IAX_COMMAND_TXACC) &&
10185 (f.subclass.integer != IAX_COMMAND_VNAK)) ||
10186 (f.frametype != AST_FRAME_IAX)) {
10187
10188 ast_debug(1, "Packet arrived out of order (expecting %d, got %d) (frametype = %d, subclass = %d)\n",
10189 iaxs[fr->callno]->iseqno, fr->oseqno, f.frametype, f.subclass.integer);
10190
10191
10192 if ((unsigned char) (iaxs[fr->callno]->iseqno - fr->oseqno) < 128) {
10193
10194 if ((f.frametype != AST_FRAME_IAX) ||
10195 ((f.subclass.integer != IAX_COMMAND_ACK) && (f.subclass.integer != IAX_COMMAND_INVAL))) {
10196 ast_debug(1, "Acking anyway\n");
10197
10198
10199 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
10200 }
10201 } else {
10202
10203 iax2_vnak(fr->callno);
10204 }
10205 ast_variables_destroy(ies.vars);
10206 ast_mutex_unlock(&iaxsl[fr->callno]);
10207 return 1;
10208 }
10209 } else {
10210
10211 if (((f.subclass.integer != IAX_COMMAND_ACK) &&
10212 (f.subclass.integer != IAX_COMMAND_INVAL) &&
10213 (f.subclass.integer != IAX_COMMAND_TXCNT) &&
10214 (f.subclass.integer != IAX_COMMAND_TXACC) &&
10215 (f.subclass.integer != IAX_COMMAND_VNAK)) ||
10216 (f.frametype != AST_FRAME_IAX))
10217 iaxs[fr->callno]->iseqno++;
10218 }
10219
10220 if (f.frametype == AST_FRAME_TEXT && thread->buf[res - 1] != '\0') {
10221 if (res < thread->buf_size)
10222 thread->buf[res++] = '\0';
10223 else
10224 thread->buf[res - 1] = '\0';
10225 }
10226
10227
10228
10229 if (!inaddrcmp(&sin, &iaxs[fr->callno]->addr) &&
10230 ((f.subclass.integer != IAX_COMMAND_INVAL) ||
10231 (f.frametype != AST_FRAME_IAX))) {
10232 unsigned char x;
10233 int call_to_destroy;
10234
10235 if (iaxs[fr->callno]->rseqno >= iaxs[fr->callno]->oseqno || (fr->iseqno >= iaxs[fr->callno]->rseqno && fr->iseqno < iaxs[fr->callno]->oseqno))
10236 x = fr->iseqno;
10237 else
10238 x = iaxs[fr->callno]->oseqno;
10239 if ((x != iaxs[fr->callno]->oseqno) || (iaxs[fr->callno]->oseqno == fr->iseqno)) {
10240
10241
10242 for (x=iaxs[fr->callno]->rseqno; x != fr->iseqno; x++) {
10243
10244 if (iaxdebug)
10245 ast_debug(1, "Cancelling transmission of packet %d\n", x);
10246 call_to_destroy = 0;
10247 AST_LIST_TRAVERSE(&frame_queue[fr->callno], cur, list) {
10248
10249 if (x == cur->oseqno) {
10250 cur->retries = -1;
10251
10252 if (cur->final)
10253 call_to_destroy = fr->callno;
10254 }
10255 }
10256 if (call_to_destroy) {
10257 if (iaxdebug)
10258 ast_debug(1, "Really destroying %d, having been acked on final message\n", call_to_destroy);
10259 ast_mutex_lock(&iaxsl[call_to_destroy]);
10260 iax2_destroy(call_to_destroy);
10261 ast_mutex_unlock(&iaxsl[call_to_destroy]);
10262 }
10263 }
10264
10265 if (iaxs[fr->callno])
10266 iaxs[fr->callno]->rseqno = fr->iseqno;
10267 else {
10268
10269 ast_variables_destroy(ies.vars);
10270 ast_mutex_unlock(&iaxsl[fr->callno]);
10271 return 1;
10272 }
10273 } else {
10274 ast_debug(1, "Received iseqno %d not within window %d->%d\n", fr->iseqno, iaxs[fr->callno]->rseqno, iaxs[fr->callno]->oseqno);
10275 }
10276 }
10277 if (inaddrcmp(&sin, &iaxs[fr->callno]->addr) &&
10278 ((f.frametype != AST_FRAME_IAX) ||
10279 ((f.subclass.integer != IAX_COMMAND_TXACC) &&
10280 (f.subclass.integer != IAX_COMMAND_TXCNT)))) {
10281
10282 ast_variables_destroy(ies.vars);
10283 ast_mutex_unlock(&iaxsl[fr->callno]);
10284 return 1;
10285 }
10286
10287
10288
10289
10290 if ((f.frametype == AST_FRAME_VOICE) ||
10291 (f.frametype == AST_FRAME_VIDEO) ||
10292 (f.frametype == AST_FRAME_IAX)) {
10293 if (ast_test_flag64(iaxs[fr->callno], IAX_DELAYPBXSTART)) {
10294 ast_clear_flag64(iaxs[fr->callno], IAX_DELAYPBXSTART);
10295 if (!ast_iax2_new(fr->callno, AST_STATE_RING, iaxs[fr->callno]->chosenformat, NULL)) {
10296 ast_variables_destroy(ies.vars);
10297 ast_mutex_unlock(&iaxsl[fr->callno]);
10298 return 1;
10299 }
10300 }
10301
10302 if (ies.vars) {
10303 struct ast_datastore *variablestore = NULL;
10304 struct ast_variable *var, *prev = NULL;
10305 AST_LIST_HEAD(, ast_var_t) *varlist;
10306
10307 iax2_lock_owner(fr->callno);
10308 if (!iaxs[fr->callno]) {
10309 ast_variables_destroy(ies.vars);
10310 ast_mutex_unlock(&iaxsl[fr->callno]);
10311 return 1;
10312 }
10313 if ((c = iaxs[fr->callno]->owner)) {
10314 varlist = ast_calloc(1, sizeof(*varlist));
10315 variablestore = ast_datastore_alloc(&iax2_variable_datastore_info, NULL);
10316
10317 if (variablestore && varlist) {
10318 variablestore->data = varlist;
10319 variablestore->inheritance = DATASTORE_INHERIT_FOREVER;
10320 AST_LIST_HEAD_INIT(varlist);
10321 ast_debug(1, "I can haz IAX vars?\n");
10322 for (var = ies.vars; var; var = var->next) {
10323 struct ast_var_t *newvar = ast_var_assign(var->name, var->value);
10324 if (prev) {
10325 ast_free(prev);
10326 }
10327 prev = var;
10328 if (!newvar) {
10329
10330 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
10331 } else {
10332 AST_LIST_INSERT_TAIL(varlist, newvar, entries);
10333 }
10334 }
10335 if (prev) {
10336 ast_free(prev);
10337 }
10338 ies.vars = NULL;
10339 ast_channel_datastore_add(c, variablestore);
10340 } else {
10341 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
10342 if (variablestore) {
10343 ast_datastore_free(variablestore);
10344 }
10345 if (varlist) {
10346 ast_free(varlist);
10347 }
10348 }
10349 ast_channel_unlock(c);
10350 } else {
10351
10352
10353 ast_debug(1, "No channel, so populating IAXVARs to the pvt, as an intermediate step.\n");
10354 for (var = ies.vars; var && var->next; var = var->next);
10355 if (var) {
10356 var->next = iaxs[fr->callno]->iaxvars;
10357 iaxs[fr->callno]->iaxvars = ies.vars;
10358 ies.vars = NULL;
10359 }
10360 }
10361 }
10362
10363 if (ies.vars) {
10364 ast_debug(1, "I have IAX variables, but they were not processed\n");
10365 }
10366 }
10367
10368
10369
10370 if ((f.frametype == AST_FRAME_IAX) && (f.subclass.integer != IAX_COMMAND_CALLTOKEN) && iaxs[fr->callno]->hold_signaling) {
10371 send_signaling(iaxs[fr->callno]);
10372 }
10373
10374 if (f.frametype == AST_FRAME_VOICE) {
10375 if (f.subclass.codec != iaxs[fr->callno]->voiceformat) {
10376 iaxs[fr->callno]->voiceformat = f.subclass.codec;
10377 ast_debug(1, "Ooh, voice format changed to '%s'\n", ast_getformatname(f.subclass.codec));
10378 if (iaxs[fr->callno]->owner) {
10379 iax2_lock_owner(fr->callno);
10380 if (iaxs[fr->callno]) {
10381 if (iaxs[fr->callno]->owner) {
10382 format_t orignative;
10383
10384 orignative = iaxs[fr->callno]->owner->nativeformats;
10385 iaxs[fr->callno]->owner->nativeformats = f.subclass.codec;
10386 if (iaxs[fr->callno]->owner->readformat)
10387 ast_set_read_format(iaxs[fr->callno]->owner, iaxs[fr->callno]->owner->readformat);
10388 iaxs[fr->callno]->owner->nativeformats = orignative;
10389 ast_channel_unlock(iaxs[fr->callno]->owner);
10390 }
10391 } else {
10392 ast_debug(1, "Neat, somebody took away the channel at a magical time but i found it!\n");
10393
10394 if (ies.vars) {
10395 ast_variables_destroy(ies.vars);
10396 ast_debug(1, "I can haz iaxvars, but they is no good. :-(\n");
10397 ies.vars = NULL;
10398 }
10399 ast_mutex_unlock(&iaxsl[fr->callno]);
10400 return 1;
10401 }
10402 }
10403 }
10404 }
10405 if (f.frametype == AST_FRAME_VIDEO) {
10406 if (f.subclass.codec != iaxs[fr->callno]->videoformat) {
10407 ast_debug(1, "Ooh, video format changed to %s\n", ast_getformatname(f.subclass.codec & ~0x1LL));
10408 iaxs[fr->callno]->videoformat = f.subclass.codec & ~0x1LL;
10409 }
10410 }
10411 if (f.frametype == AST_FRAME_CONTROL && iaxs[fr->callno]->owner) {
10412 if (f.subclass.integer == AST_CONTROL_BUSY) {
10413 iaxs[fr->callno]->owner->hangupcause = AST_CAUSE_BUSY;
10414 } else if (f.subclass.integer == AST_CONTROL_CONGESTION) {
10415 iaxs[fr->callno]->owner->hangupcause = AST_CAUSE_CONGESTION;
10416 }
10417 }
10418 if (f.frametype == AST_FRAME_IAX) {
10419 ast_sched_thread_del(sched, iaxs[fr->callno]->initid);
10420
10421 if (iaxdebug)
10422 ast_debug(1, "IAX subclass %d received\n", f.subclass.integer);
10423
10424
10425 if (iaxs[fr->callno]->last < fr->ts &&
10426 f.subclass.integer != IAX_COMMAND_ACK &&
10427 f.subclass.integer != IAX_COMMAND_PONG &&
10428 f.subclass.integer != IAX_COMMAND_LAGRP) {
10429 iaxs[fr->callno]->last = fr->ts;
10430 if (iaxdebug)
10431 ast_debug(1, "For call=%d, set last=%d\n", fr->callno, fr->ts);
10432 }
10433 iaxs[fr->callno]->last_iax_message = f.subclass.integer;
10434 if (!iaxs[fr->callno]->first_iax_message) {
10435 iaxs[fr->callno]->first_iax_message = f.subclass.integer;
10436 }
10437 switch(f.subclass.integer) {
10438 case IAX_COMMAND_ACK:
10439
10440 break;
10441 case IAX_COMMAND_QUELCH:
10442 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED)) {
10443
10444 if (iaxs[fr->callno]->owner) {
10445 ast_manager_event(iaxs[fr->callno]->owner, EVENT_FLAG_CALL, "Hold",
10446 "Status: On\r\n"
10447 "Channel: %s\r\n"
10448 "Uniqueid: %s\r\n",
10449 iaxs[fr->callno]->owner->name,
10450 iaxs[fr->callno]->owner->uniqueid);
10451 }
10452
10453 ast_set_flag64(iaxs[fr->callno], IAX_QUELCH);
10454 if (ies.musiconhold) {
10455 iax2_lock_owner(fr->callno);
10456 if (!iaxs[fr->callno] || !iaxs[fr->callno]->owner) {
10457 break;
10458 }
10459 if (ast_bridged_channel(iaxs[fr->callno]->owner)) {
10460 const char *moh_suggest = iaxs[fr->callno]->mohsuggest;
10461
10462
10463
10464
10465
10466 iax2_queue_control_data(fr->callno, AST_CONTROL_HOLD,
10467 S_OR(moh_suggest, NULL),
10468 !ast_strlen_zero(moh_suggest) ? strlen(moh_suggest) + 1 : 0);
10469 }
10470 ast_channel_unlock(iaxs[fr->callno]->owner);
10471 }
10472 }
10473 break;
10474 case IAX_COMMAND_UNQUELCH:
10475 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED)) {
10476 iax2_lock_owner(fr->callno);
10477 if (!iaxs[fr->callno]) {
10478 break;
10479 }
10480
10481 if (iaxs[fr->callno]->owner && ast_test_flag64(iaxs[fr->callno], IAX_QUELCH)) {
10482 ast_manager_event(iaxs[fr->callno]->owner, EVENT_FLAG_CALL, "Hold",
10483 "Status: Off\r\n"
10484 "Channel: %s\r\n"
10485 "Uniqueid: %s\r\n",
10486 iaxs[fr->callno]->owner->name,
10487 iaxs[fr->callno]->owner->uniqueid);
10488 }
10489
10490 ast_clear_flag64(iaxs[fr->callno], IAX_QUELCH);
10491 if (!iaxs[fr->callno]->owner) {
10492 break;
10493 }
10494 if (ast_bridged_channel(iaxs[fr->callno]->owner)) {
10495
10496
10497
10498
10499 iax2_queue_control_data(fr->callno, AST_CONTROL_UNHOLD, NULL, 0);
10500 }
10501 ast_channel_unlock(iaxs[fr->callno]->owner);
10502 }
10503 break;
10504 case IAX_COMMAND_TXACC:
10505 if (iaxs[fr->callno]->transferring == TRANSFER_BEGIN) {
10506
10507 AST_LIST_TRAVERSE(&frame_queue[fr->callno], cur, list) {
10508
10509 if (cur->transfer) {
10510 cur->retries = -1;
10511 }
10512 }
10513 memset(&ied1, 0, sizeof(ied1));
10514 iax_ie_append_short(&ied1, IAX_IE_CALLNO, iaxs[fr->callno]->callno);
10515 send_command(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_TXREADY, 0, ied1.buf, ied1.pos, -1);
10516 iaxs[fr->callno]->transferring = TRANSFER_READY;
10517 }
10518 break;
10519 case IAX_COMMAND_NEW:
10520
10521 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED | IAX_STATE_TBD))
10522 break;
10523 if (ies.provverpres && ies.serviceident && sin.sin_addr.s_addr) {
10524 ast_mutex_unlock(&iaxsl[fr->callno]);
10525 check_provisioning(&sin, fd, ies.serviceident, ies.provver);
10526 ast_mutex_lock(&iaxsl[fr->callno]);
10527 if (!iaxs[fr->callno]) {
10528 break;
10529 }
10530 }
10531
10532 if (ast_test_flag64(iaxs[fr->callno], IAX_TRUNK)) {
10533 int new_callno;
10534 if ((new_callno = make_trunk(fr->callno, 1)) != -1)
10535 fr->callno = new_callno;
10536 }
10537
10538 if (delayreject)
10539 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
10540 if (check_access(fr->callno, &sin, &ies)) {
10541
10542 auth_fail(fr->callno, IAX_COMMAND_REJECT);
10543 if (authdebug)
10544 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, who was trying to reach '%s@%s'\n", ast_inet_ntoa(sin.sin_addr), iaxs[fr->callno]->exten, iaxs[fr->callno]->context);
10545 break;
10546 }
10547 if (ast_strlen_zero(iaxs[fr->callno]->secret) && ast_test_flag64(iaxs[fr->callno], IAX_FORCE_ENCRYPT)) {
10548 auth_fail(fr->callno, IAX_COMMAND_REJECT);
10549 ast_log(LOG_WARNING, "Rejected connect attempt. No secret present while force encrypt enabled.\n");
10550 break;
10551 }
10552 if (strcasecmp(iaxs[fr->callno]->exten, "TBD")) {
10553 const char *context, *exten, *cid_num;
10554
10555 context = ast_strdupa(iaxs[fr->callno]->context);
10556 exten = ast_strdupa(iaxs[fr->callno]->exten);
10557 cid_num = ast_strdupa(iaxs[fr->callno]->cid_num);
10558
10559
10560 ast_mutex_unlock(&iaxsl[fr->callno]);
10561 exists = ast_exists_extension(NULL, context, exten, 1, cid_num);
10562 ast_mutex_lock(&iaxsl[fr->callno]);
10563
10564 if (!iaxs[fr->callno]) {
10565 break;
10566 }
10567 } else
10568 exists = 0;
10569
10570 save_osptoken(fr, &ies);
10571 if (ast_strlen_zero(iaxs[fr->callno]->secret) && ast_strlen_zero(iaxs[fr->callno]->inkeys)) {
10572 if (strcmp(iaxs[fr->callno]->exten, "TBD") && !exists) {
10573 memset(&ied0, 0, sizeof(ied0));
10574 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "No such context/extension");
10575 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_NO_ROUTE_DESTINATION);
10576 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
10577 if (!iaxs[fr->callno]) {
10578 break;
10579 }
10580 if (authdebug)
10581 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, request '%s@%s' does not exist\n", ast_inet_ntoa(sin.sin_addr), iaxs[fr->callno]->exten, iaxs[fr->callno]->context);
10582 } else {
10583
10584
10585 if(ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOPREFS)) {
10586 if(ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP)) {
10587 using_prefs = "reqonly";
10588 } else {
10589 using_prefs = "disabled";
10590 }
10591 format = iaxs[fr->callno]->peerformat & iaxs[fr->callno]->capability;
10592 memset(&pref, 0, sizeof(pref));
10593 strcpy(caller_pref_buf, "disabled");
10594 strcpy(host_pref_buf, "disabled");
10595 } else {
10596 using_prefs = "mine";
10597
10598 if (ies.codec_prefs)
10599 ast_codec_pref_convert(&iaxs[fr->callno]->rprefs, ies.codec_prefs, 32, 0);
10600 if (ast_codec_pref_index(&iaxs[fr->callno]->rprefs, 0)) {
10601
10602 if (ast_test_flag64(iaxs[fr->callno], IAX_CODEC_USER_FIRST)) {
10603 pref = iaxs[fr->callno]->rprefs;
10604 using_prefs = "caller";
10605 } else {
10606 pref = iaxs[fr->callno]->prefs;
10607 }
10608 } else
10609 pref = iaxs[fr->callno]->prefs;
10610
10611 format = ast_codec_choose(&pref, iaxs[fr->callno]->capability & iaxs[fr->callno]->peercapability, 0);
10612 ast_codec_pref_string(&iaxs[fr->callno]->rprefs, caller_pref_buf, sizeof(caller_pref_buf) - 1);
10613 ast_codec_pref_string(&iaxs[fr->callno]->prefs, host_pref_buf, sizeof(host_pref_buf) - 1);
10614 }
10615 if (!format) {
10616 if(!ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP))
10617 format = iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability;
10618 if (!format) {
10619 memset(&ied0, 0, sizeof(ied0));
10620 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "Unable to negotiate codec");
10621 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_BEARERCAPABILITY_NOTAVAIL);
10622 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
10623 if (!iaxs[fr->callno]) {
10624 break;
10625 }
10626 if (authdebug) {
10627 char tmp[256], tmp2[256], tmp3[256];
10628 if (ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP)) {
10629 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, requested '%s' incompatible with our capability '%s'.\n",
10630 ast_inet_ntoa(sin.sin_addr),
10631 ast_getformatname_multiple(tmp, sizeof(tmp), iaxs[fr->callno]->peerformat),
10632 ast_getformatname_multiple(tmp2, sizeof(tmp2), iaxs[fr->callno]->capability));
10633 } else {
10634 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, requested/capability '%s'/'%s' incompatible with our capability '%s'.\n",
10635 ast_inet_ntoa(sin.sin_addr),
10636 ast_getformatname_multiple(tmp, sizeof(tmp), iaxs[fr->callno]->peerformat),
10637 ast_getformatname_multiple(tmp2, sizeof(tmp2), iaxs[fr->callno]->peercapability),
10638 ast_getformatname_multiple(tmp3, sizeof(tmp3), iaxs[fr->callno]->capability));
10639 }
10640 }
10641 } else {
10642
10643 if(ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP)) {
10644 if(!(iaxs[fr->callno]->peerformat & iaxs[fr->callno]->capability))
10645 format = 0;
10646 } else {
10647 if(ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOPREFS)) {
10648 using_prefs = ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP) ? "reqonly" : "disabled";
10649 memset(&pref, 0, sizeof(pref));
10650 format = ast_best_codec(iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability);
10651 strcpy(caller_pref_buf,"disabled");
10652 strcpy(host_pref_buf,"disabled");
10653 } else {
10654 using_prefs = "mine";
10655 if (ast_codec_pref_index(&iaxs[fr->callno]->rprefs, 0)) {
10656
10657 if (ast_test_flag64(iaxs[fr->callno], IAX_CODEC_USER_FIRST)) {
10658 pref = iaxs[fr->callno]->prefs;
10659 } else {
10660 pref = iaxs[fr->callno]->rprefs;
10661 using_prefs = "caller";
10662 }
10663 format = ast_codec_choose(&pref, iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability, 1);
10664 } else
10665 format = ast_best_codec(iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability);
10666 }
10667 }
10668
10669 if (!format) {
10670 char tmp[256], tmp2[256], tmp3[256];
10671 memset(&ied0, 0, sizeof(ied0));
10672 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "Unable to negotiate codec");
10673 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_BEARERCAPABILITY_NOTAVAIL);
10674 ast_log(LOG_ERROR, "No best format in '%s'???\n", ast_getformatname_multiple(tmp, sizeof(tmp), iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability));
10675 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
10676 if (!iaxs[fr->callno]) {
10677 break;
10678 }
10679 if (authdebug) {
10680 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, requested/capability '%s'/'%s' incompatible with our capability '%s'.\n",
10681 ast_inet_ntoa(sin.sin_addr),
10682 ast_getformatname_multiple(tmp, sizeof(tmp), iaxs[fr->callno]->peerformat),
10683 ast_getformatname_multiple(tmp2, sizeof(tmp2), iaxs[fr->callno]->peercapability),
10684 ast_getformatname_multiple(tmp3, sizeof(tmp3), iaxs[fr->callno]->capability));
10685 }
10686 ast_set_flag64(iaxs[fr->callno], IAX_ALREADYGONE);
10687 break;
10688 }
10689 }
10690 }
10691 if (format) {
10692
10693 memset(&ied1, 0, sizeof(ied1));
10694 iax_ie_append_int(&ied1, IAX_IE_FORMAT, format);
10695 iax_ie_append_versioned_uint64(&ied1, IAX_IE_FORMAT2, 0, format);
10696 send_command(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACCEPT, 0, ied1.buf, ied1.pos, -1);
10697 if (strcmp(iaxs[fr->callno]->exten, "TBD")) {
10698 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED);
10699 ast_verb(3, "Accepting UNAUTHENTICATED call from %s:\n"
10700 "%srequested format = %s,\n"
10701 "%srequested prefs = %s,\n"
10702 "%sactual format = %s,\n"
10703 "%shost prefs = %s,\n"
10704 "%spriority = %s\n",
10705 ast_inet_ntoa(sin.sin_addr),
10706 VERBOSE_PREFIX_4,
10707 ast_getformatname(iaxs[fr->callno]->peerformat),
10708 VERBOSE_PREFIX_4,
10709 caller_pref_buf,
10710 VERBOSE_PREFIX_4,
10711 ast_getformatname(format),
10712 VERBOSE_PREFIX_4,
10713 host_pref_buf,
10714 VERBOSE_PREFIX_4,
10715 using_prefs);
10716
10717 iaxs[fr->callno]->chosenformat = format;
10718 ast_set_flag64(iaxs[fr->callno], IAX_DELAYPBXSTART);
10719 } else {
10720 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_TBD);
10721
10722 ast_verb(3, "Accepted unauthenticated TBD call from %s\n", ast_inet_ntoa(sin.sin_addr));
10723 }
10724 }
10725 }
10726 break;
10727 }
10728 if (iaxs[fr->callno]->authmethods & IAX_AUTH_MD5)
10729 merge_encryption(iaxs[fr->callno],ies.encmethods);
10730 else
10731 iaxs[fr->callno]->encmethods = 0;
10732 if (!authenticate_request(fr->callno) && iaxs[fr->callno])
10733 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_AUTHENTICATED);
10734 break;
10735 case IAX_COMMAND_DPREQ:
10736
10737 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_TBD) &&
10738 !ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED) && ies.called_number) {
10739 if (iaxcompat) {
10740
10741 spawn_dp_lookup(fr->callno, iaxs[fr->callno]->context, ies.called_number, iaxs[fr->callno]->cid_num);
10742 } else {
10743
10744 dp_lookup(fr->callno, iaxs[fr->callno]->context, ies.called_number, iaxs[fr->callno]->cid_num, 1);
10745 }
10746 }
10747 break;
10748 case IAX_COMMAND_HANGUP:
10749 ast_set_flag64(iaxs[fr->callno], IAX_ALREADYGONE);
10750 ast_debug(1, "Immediately destroying %d, having received hangup\n", fr->callno);
10751
10752 if (iaxs[fr->callno]->owner) {
10753 set_hangup_source_and_cause(fr->callno, ies.causecode);
10754 if (!iaxs[fr->callno]) {
10755 break;
10756 }
10757 }
10758
10759
10760 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
10761 iax2_destroy(fr->callno);
10762 break;
10763 case IAX_COMMAND_REJECT:
10764
10765 if (iaxs[fr->callno]->owner) {
10766 set_hangup_source_and_cause(fr->callno, ies.causecode);
10767 if (!iaxs[fr->callno]) {
10768 break;
10769 }
10770 }
10771
10772 if (!ast_test_flag64(iaxs[fr->callno], IAX_PROVISION)) {
10773 if (iaxs[fr->callno]->owner && authdebug)
10774 ast_log(LOG_WARNING, "Call rejected by %s: %s\n",
10775 ast_inet_ntoa(iaxs[fr->callno]->addr.sin_addr),
10776 ies.cause ? ies.cause : "<Unknown>");
10777 ast_debug(1, "Immediately destroying %d, having received reject\n",
10778 fr->callno);
10779 }
10780
10781 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK,
10782 fr->ts, NULL, 0, fr->iseqno);
10783 if (!ast_test_flag64(iaxs[fr->callno], IAX_PROVISION))
10784 iaxs[fr->callno]->error = EPERM;
10785 iax2_destroy(fr->callno);
10786 break;
10787 case IAX_COMMAND_TRANSFER:
10788 {
10789 struct ast_channel *bridged_chan;
10790 struct ast_channel *owner;
10791
10792 iax2_lock_owner(fr->callno);
10793 if (!iaxs[fr->callno]) {
10794
10795 break;
10796 }
10797 owner = iaxs[fr->callno]->owner;
10798 bridged_chan = owner ? ast_bridged_channel(owner) : NULL;
10799 if (bridged_chan && ies.called_number) {
10800 const char *context;
10801
10802 context = ast_strdupa(iaxs[fr->callno]->context);
10803
10804 ast_channel_ref(owner);
10805 ast_channel_ref(bridged_chan);
10806 ast_channel_unlock(owner);
10807 ast_mutex_unlock(&iaxsl[fr->callno]);
10808
10809
10810 pbx_builtin_setvar_helper(owner, "BLINDTRANSFER", bridged_chan->name);
10811 pbx_builtin_setvar_helper(bridged_chan, "BLINDTRANSFER", owner->name);
10812
10813
10814 if (ast_parking_ext_valid(ies.called_number, owner, context)) {
10815 ast_debug(1, "Parking call '%s'\n", bridged_chan->name);
10816 if (iax_park(bridged_chan, owner, ies.called_number, context)) {
10817 ast_log(LOG_WARNING, "Failed to park call '%s'\n",
10818 bridged_chan->name);
10819 }
10820 } else {
10821 if (ast_async_goto(bridged_chan, context, ies.called_number, 1)) {
10822 ast_log(LOG_WARNING,
10823 "Async goto of '%s' to '%s@%s' failed\n",
10824 bridged_chan->name, ies.called_number, context);
10825 } else {
10826 ast_debug(1, "Async goto of '%s' to '%s@%s' started\n",
10827 bridged_chan->name, ies.called_number, context);
10828 }
10829 }
10830 ast_channel_unref(owner);
10831 ast_channel_unref(bridged_chan);
10832
10833 ast_mutex_lock(&iaxsl[fr->callno]);
10834 } else {
10835 ast_debug(1, "Async goto not applicable on call %d\n", fr->callno);
10836 if (owner) {
10837 ast_channel_unlock(owner);
10838 }
10839 }
10840
10841 break;
10842 }
10843 case IAX_COMMAND_ACCEPT:
10844
10845 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED | IAX_STATE_TBD | IAX_STATE_AUTHENTICATED))
10846 break;
10847 if (ast_test_flag64(iaxs[fr->callno], IAX_PROVISION)) {
10848
10849 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
10850 iax2_destroy(fr->callno);
10851 break;
10852 }
10853 if (ies.format) {
10854 iaxs[fr->callno]->peerformat = ies.format;
10855 } else {
10856 if (iaxs[fr->callno]->owner)
10857 iaxs[fr->callno]->peerformat = iaxs[fr->callno]->owner->nativeformats;
10858 else
10859 iaxs[fr->callno]->peerformat = iaxs[fr->callno]->capability;
10860 }
10861 ast_verb(3, "Call accepted by %s (format %s)\n", ast_inet_ntoa(iaxs[fr->callno]->addr.sin_addr), ast_getformatname(iaxs[fr->callno]->peerformat));
10862 if (!(iaxs[fr->callno]->peerformat & iaxs[fr->callno]->capability)) {
10863 memset(&ied0, 0, sizeof(ied0));
10864 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "Unable to negotiate codec");
10865 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_BEARERCAPABILITY_NOTAVAIL);
10866 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
10867 if (!iaxs[fr->callno]) {
10868 break;
10869 }
10870 if (authdebug) {
10871 char tmp1[256], tmp2[256];
10872 ast_log(LOG_NOTICE, "Rejected call to %s, format %s incompatible with our capability %s.\n",
10873 ast_inet_ntoa(sin.sin_addr),
10874 ast_getformatname_multiple(tmp1, sizeof(tmp1), iaxs[fr->callno]->peerformat),
10875 ast_getformatname_multiple(tmp2, sizeof(tmp2), iaxs[fr->callno]->capability));
10876 }
10877 } else {
10878 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED);
10879 iax2_lock_owner(fr->callno);
10880 if (iaxs[fr->callno] && iaxs[fr->callno]->owner) {
10881
10882 iaxs[fr->callno]->owner->nativeformats = iaxs[fr->callno]->peerformat;
10883 ast_verb(3, "Format for call is %s\n", ast_getformatname(iaxs[fr->callno]->owner->nativeformats));
10884
10885
10886 if (iaxs[fr->callno]->owner->writeformat)
10887 ast_set_write_format(iaxs[fr->callno]->owner, iaxs[fr->callno]->owner->writeformat);
10888 if (iaxs[fr->callno]->owner->readformat)
10889 ast_set_read_format(iaxs[fr->callno]->owner, iaxs[fr->callno]->owner->readformat);
10890 ast_channel_unlock(iaxs[fr->callno]->owner);
10891 }
10892 }
10893 if (iaxs[fr->callno]) {
10894 AST_LIST_LOCK(&dpcache);
10895 AST_LIST_TRAVERSE(&iaxs[fr->callno]->dpentries, dp, peer_list)
10896 if (!(dp->flags & CACHE_FLAG_TRANSMITTED))
10897 iax2_dprequest(dp, fr->callno);
10898 AST_LIST_UNLOCK(&dpcache);
10899 }
10900 break;
10901 case IAX_COMMAND_POKE:
10902
10903 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_PONG, fr->ts, NULL, 0, -1);
10904 break;
10905 case IAX_COMMAND_PING:
10906 {
10907 struct iax_ie_data pingied;
10908 construct_rr(iaxs[fr->callno], &pingied);
10909
10910 send_command(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_PONG, fr->ts, pingied.buf, pingied.pos, -1);
10911 }
10912 break;
10913 case IAX_COMMAND_PONG:
10914
10915 iaxs[fr->callno]->pingtime = calc_timestamp(iaxs[fr->callno], 0, &f) - fr->ts;
10916
10917 save_rr(fr, &ies);
10918
10919
10920 log_jitterstats(fr->callno);
10921
10922 if (iaxs[fr->callno]->peerpoke) {
10923 peer = iaxs[fr->callno]->peerpoke;
10924 if ((peer->lastms < 0) || (peer->historicms > peer->maxms)) {
10925 if (iaxs[fr->callno]->pingtime <= peer->maxms) {
10926 ast_log(LOG_NOTICE, "Peer '%s' is now REACHABLE! Time: %d\n", peer->name, iaxs[fr->callno]->pingtime);
10927 manager_event(EVENT_FLAG_SYSTEM, "PeerStatus", "ChannelType: IAX2\r\nPeer: IAX2/%s\r\nPeerStatus: Reachable\r\nTime: %d\r\n", peer->name, iaxs[fr->callno]->pingtime);
10928 ast_devstate_changed(AST_DEVICE_NOT_INUSE, "IAX2/%s", peer->name);
10929 }
10930 } else if ((peer->historicms > 0) && (peer->historicms <= peer->maxms)) {
10931 if (iaxs[fr->callno]->pingtime > peer->maxms) {
10932 ast_log(LOG_NOTICE, "Peer '%s' is now TOO LAGGED (%d ms)!\n", peer->name, iaxs[fr->callno]->pingtime);
10933 manager_event(EVENT_FLAG_SYSTEM, "PeerStatus", "ChannelType: IAX2\r\nPeer: IAX2/%s\r\nPeerStatus: Lagged\r\nTime: %d\r\n", peer->name, iaxs[fr->callno]->pingtime);
10934 ast_devstate_changed(AST_DEVICE_UNAVAILABLE, "IAX2/%s", peer->name);
10935 }
10936 }
10937 peer->lastms = iaxs[fr->callno]->pingtime;
10938 if (peer->smoothing && (peer->lastms > -1))
10939 peer->historicms = (iaxs[fr->callno]->pingtime + peer->historicms) / 2;
10940 else if (peer->smoothing && peer->lastms < 0)
10941 peer->historicms = (0 + peer->historicms) / 2;
10942 else
10943 peer->historicms = iaxs[fr->callno]->pingtime;
10944
10945
10946 if (peer->pokeexpire > -1) {
10947 if (!ast_sched_thread_del(sched, peer->pokeexpire)) {
10948 peer_unref(peer);
10949 peer->pokeexpire = -1;
10950 }
10951 }
10952
10953 if ((peer->lastms < 0) || (peer->historicms > peer->maxms))
10954 peer->pokeexpire = iax2_sched_add(sched, peer->pokefreqnotok, iax2_poke_peer_s, peer_ref(peer));
10955 else
10956 peer->pokeexpire = iax2_sched_add(sched, peer->pokefreqok, iax2_poke_peer_s, peer_ref(peer));
10957 if (peer->pokeexpire == -1)
10958 peer_unref(peer);
10959
10960 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
10961
10962 iax2_destroy(fr->callno);
10963 peer->callno = 0;
10964 ast_debug(1, "Peer %s: got pong, lastms %d, historicms %d, maxms %d\n", peer->name, peer->lastms, peer->historicms, peer->maxms);
10965 }
10966 break;
10967 case IAX_COMMAND_LAGRQ:
10968 case IAX_COMMAND_LAGRP:
10969 f.src = "LAGRQ";
10970 f.mallocd = 0;
10971 f.offset = 0;
10972 f.samples = 0;
10973 iax_frame_wrap(fr, &f);
10974 if (f.subclass.integer == IAX_COMMAND_LAGRQ) {
10975
10976 fr->af.subclass.integer = IAX_COMMAND_LAGRP;
10977 iax2_send(iaxs[fr->callno], &fr->af, fr->ts, -1, 0, 0, 0);
10978 } else {
10979
10980 unsigned int ts;
10981
10982 ts = calc_timestamp(iaxs[fr->callno], 0, &fr->af);
10983 iaxs[fr->callno]->lag = ts - fr->ts;
10984 if (iaxdebug)
10985 ast_debug(1, "Peer %s lag measured as %dms\n",
10986 ast_inet_ntoa(iaxs[fr->callno]->addr.sin_addr), iaxs[fr->callno]->lag);
10987 }
10988 break;
10989 case IAX_COMMAND_AUTHREQ:
10990 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED | IAX_STATE_TBD)) {
10991 ast_log(LOG_WARNING, "Call on %s is already up, can't start on it\n", iaxs[fr->callno]->owner ? iaxs[fr->callno]->owner->name : "<Unknown>");
10992 break;
10993 }
10994 if (authenticate_reply(iaxs[fr->callno], &iaxs[fr->callno]->addr, &ies, iaxs[fr->callno]->secret, iaxs[fr->callno]->outkey)) {
10995 struct ast_frame hangup_fr = { .frametype = AST_FRAME_CONTROL,
10996 .subclass.integer = AST_CONTROL_HANGUP,
10997 };
10998 ast_log(LOG_WARNING,
10999 "I don't know how to authenticate %s to %s\n",
11000 ies.username ? ies.username : "<unknown>", ast_inet_ntoa(iaxs[fr->callno]->addr.sin_addr));
11001 iax2_queue_frame(fr->callno, &hangup_fr);
11002 }
11003 break;
11004 case IAX_COMMAND_AUTHREP:
11005
11006 if (delayreject)
11007 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
11008
11009 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED | IAX_STATE_TBD)) {
11010 ast_log(LOG_WARNING, "Call on %s is already up, can't start on it\n", iaxs[fr->callno]->owner ? iaxs[fr->callno]->owner->name : "<Unknown>");
11011 break;
11012 }
11013 if (authenticate_verify(iaxs[fr->callno], &ies)) {
11014 if (authdebug)
11015 ast_log(LOG_NOTICE, "Host %s failed to authenticate as %s\n", ast_inet_ntoa(iaxs[fr->callno]->addr.sin_addr), iaxs[fr->callno]->username);
11016 memset(&ied0, 0, sizeof(ied0));
11017 auth_fail(fr->callno, IAX_COMMAND_REJECT);
11018 break;
11019 }
11020 if (strcasecmp(iaxs[fr->callno]->exten, "TBD")) {
11021
11022 exists = ast_exists_extension(NULL, iaxs[fr->callno]->context, iaxs[fr->callno]->exten, 1, iaxs[fr->callno]->cid_num);
11023 } else
11024 exists = 0;
11025 if (strcmp(iaxs[fr->callno]->exten, "TBD") && !exists) {
11026 if (authdebug)
11027 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, request '%s@%s' does not exist\n", ast_inet_ntoa(sin.sin_addr), iaxs[fr->callno]->exten, iaxs[fr->callno]->context);
11028 memset(&ied0, 0, sizeof(ied0));
11029 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "No such context/extension");
11030 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_NO_ROUTE_DESTINATION);
11031 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
11032 if (!iaxs[fr->callno]) {
11033 break;
11034 }
11035 } else {
11036
11037 if(ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOPREFS)) {
11038 if(ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP)) {
11039 using_prefs = "reqonly";
11040 } else {
11041 using_prefs = "disabled";
11042 }
11043 format = iaxs[fr->callno]->peerformat & iaxs[fr->callno]->capability;
11044 memset(&pref, 0, sizeof(pref));
11045 strcpy(caller_pref_buf, "disabled");
11046 strcpy(host_pref_buf, "disabled");
11047 } else {
11048 using_prefs = "mine";
11049 if (ies.codec_prefs)
11050 ast_codec_pref_convert(&iaxs[fr->callno]->rprefs, ies.codec_prefs, 32, 0);
11051 if (ast_codec_pref_index(&iaxs[fr->callno]->rprefs, 0)) {
11052 if (ast_test_flag64(iaxs[fr->callno], IAX_CODEC_USER_FIRST)) {
11053 pref = iaxs[fr->callno]->rprefs;
11054 using_prefs = "caller";
11055 } else {
11056 pref = iaxs[fr->callno]->prefs;
11057 }
11058 } else
11059 pref = iaxs[fr->callno]->prefs;
11060 format = ast_codec_choose(&pref, iaxs[fr->callno]->capability & iaxs[fr->callno]->peercapability, 0);
11061 ast_codec_pref_string(&iaxs[fr->callno]->rprefs, caller_pref_buf, sizeof(caller_pref_buf) - 1);
11062 ast_codec_pref_string(&iaxs[fr->callno]->prefs, host_pref_buf, sizeof(host_pref_buf) - 1);
11063 }
11064 if (!format) {
11065 char tmp1[256], tmp2[256], tmp3[256];
11066 if(!ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP)) {
11067 ast_debug(1, "We don't do requested format %s, falling back to peer capability '%s'\n",
11068 ast_getformatname(iaxs[fr->callno]->peerformat),
11069 ast_getformatname_multiple(tmp1, sizeof(tmp1), iaxs[fr->callno]->peercapability));
11070 format = iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability;
11071 }
11072 if (!format) {
11073 if (authdebug) {
11074 if (ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP)) {
11075 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, requested '%s' incompatible with our capability '%s'.\n", ast_inet_ntoa(sin.sin_addr),
11076 ast_getformatname_multiple(tmp1, sizeof(tmp1), iaxs[fr->callno]->peerformat),
11077 ast_getformatname_multiple(tmp2, sizeof(tmp2), iaxs[fr->callno]->capability));
11078 } else {
11079 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, requested/capability '%s'/'%s' incompatible with our capability '%s'.\n",
11080 ast_inet_ntoa(sin.sin_addr),
11081 ast_getformatname_multiple(tmp1, sizeof(tmp1), iaxs[fr->callno]->peerformat),
11082 ast_getformatname_multiple(tmp2, sizeof(tmp2), iaxs[fr->callno]->peercapability),
11083 ast_getformatname_multiple(tmp3, sizeof(tmp3), iaxs[fr->callno]->capability));
11084 }
11085 }
11086 memset(&ied0, 0, sizeof(ied0));
11087 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "Unable to negotiate codec");
11088 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_BEARERCAPABILITY_NOTAVAIL);
11089 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
11090 if (!iaxs[fr->callno]) {
11091 break;
11092 }
11093 } else {
11094
11095 if(ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP)) {
11096 if(!(iaxs[fr->callno]->peerformat & iaxs[fr->callno]->capability))
11097 format = 0;
11098 } else {
11099 if(ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOPREFS)) {
11100 using_prefs = ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP) ? "reqonly" : "disabled";
11101 memset(&pref, 0, sizeof(pref));
11102 format = ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP) ?
11103 iaxs[fr->callno]->peerformat : ast_best_codec(iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability);
11104 strcpy(caller_pref_buf,"disabled");
11105 strcpy(host_pref_buf,"disabled");
11106 } else {
11107 using_prefs = "mine";
11108 if (ast_codec_pref_index(&iaxs[fr->callno]->rprefs, 0)) {
11109
11110 if (ast_test_flag64(iaxs[fr->callno], IAX_CODEC_USER_FIRST)) {
11111 pref = iaxs[fr->callno]->prefs;
11112 } else {
11113 pref = iaxs[fr->callno]->rprefs;
11114 using_prefs = "caller";
11115 }
11116 format = ast_codec_choose(&pref, iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability, 1);
11117 } else
11118 format = ast_best_codec(iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability);
11119 }
11120 }
11121 if (!format) {
11122 char tmp1[256], tmp2[256], tmp3[256];
11123 ast_log(LOG_ERROR, "No best format in %s???\n",
11124 ast_getformatname_multiple(tmp1, sizeof(tmp1), iaxs[fr->callno]->peercapability & iaxs[fr->callno]->capability));
11125 if (authdebug) {
11126 if (ast_test_flag64(iaxs[fr->callno], IAX_CODEC_NOCAP)) {
11127 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, requested '%s' incompatible with our capability '%s'.\n",
11128 ast_inet_ntoa(sin.sin_addr),
11129 ast_getformatname_multiple(tmp1, sizeof(tmp1), iaxs[fr->callno]->peerformat),
11130 ast_getformatname_multiple(tmp2, sizeof(tmp2), iaxs[fr->callno]->capability));
11131 } else {
11132 ast_log(LOG_NOTICE, "Rejected connect attempt from %s, requested/capability '%s'/'%s' incompatible with our capability '%s'.\n",
11133 ast_inet_ntoa(sin.sin_addr),
11134 ast_getformatname_multiple(tmp1, sizeof(tmp1), iaxs[fr->callno]->peerformat),
11135 ast_getformatname_multiple(tmp2, sizeof(tmp2), iaxs[fr->callno]->peercapability),
11136 ast_getformatname_multiple(tmp3, sizeof(tmp3), iaxs[fr->callno]->capability));
11137 }
11138 }
11139 memset(&ied0, 0, sizeof(ied0));
11140 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "Unable to negotiate codec");
11141 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_BEARERCAPABILITY_NOTAVAIL);
11142 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
11143 if (!iaxs[fr->callno]) {
11144 break;
11145 }
11146 }
11147 }
11148 }
11149 if (format) {
11150
11151 memset(&ied1, 0, sizeof(ied1));
11152 iax_ie_append_int(&ied1, IAX_IE_FORMAT, format);
11153 iax_ie_append_versioned_uint64(&ied1, IAX_IE_FORMAT2, 0, format);
11154 send_command(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACCEPT, 0, ied1.buf, ied1.pos, -1);
11155 if (strcmp(iaxs[fr->callno]->exten, "TBD")) {
11156 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED);
11157 ast_verb(3, "Accepting AUTHENTICATED call from %s:\n"
11158 "%srequested format = %s,\n"
11159 "%srequested prefs = %s,\n"
11160 "%sactual format = %s,\n"
11161 "%shost prefs = %s,\n"
11162 "%spriority = %s\n",
11163 ast_inet_ntoa(sin.sin_addr),
11164 VERBOSE_PREFIX_4,
11165 ast_getformatname(iaxs[fr->callno]->peerformat),
11166 VERBOSE_PREFIX_4,
11167 caller_pref_buf,
11168 VERBOSE_PREFIX_4,
11169 ast_getformatname(format),
11170 VERBOSE_PREFIX_4,
11171 host_pref_buf,
11172 VERBOSE_PREFIX_4,
11173 using_prefs);
11174
11175 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED);
11176 if (!(c = ast_iax2_new(fr->callno, AST_STATE_RING, format, NULL)))
11177 iax2_destroy(fr->callno);
11178 else if (ies.vars) {
11179 struct ast_datastore *variablestore;
11180 struct ast_variable *var, *prev = NULL;
11181 AST_LIST_HEAD(, ast_var_t) *varlist;
11182 varlist = ast_calloc(1, sizeof(*varlist));
11183 variablestore = ast_datastore_alloc(&iax2_variable_datastore_info, NULL);
11184 if (variablestore && varlist) {
11185 variablestore->data = varlist;
11186 variablestore->inheritance = DATASTORE_INHERIT_FOREVER;
11187 AST_LIST_HEAD_INIT(varlist);
11188 ast_debug(1, "I can haz IAX vars? w00t\n");
11189 for (var = ies.vars; var; var = var->next) {
11190 struct ast_var_t *newvar = ast_var_assign(var->name, var->value);
11191 if (prev)
11192 ast_free(prev);
11193 prev = var;
11194 if (!newvar) {
11195
11196 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
11197 } else {
11198 AST_LIST_INSERT_TAIL(varlist, newvar, entries);
11199 }
11200 }
11201 if (prev)
11202 ast_free(prev);
11203 ies.vars = NULL;
11204 ast_channel_datastore_add(c, variablestore);
11205 } else {
11206 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
11207 if (variablestore)
11208 ast_datastore_free(variablestore);
11209 if (varlist)
11210 ast_free(varlist);
11211 }
11212 }
11213 } else {
11214 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_TBD);
11215
11216 ast_verb(3, "Accepted AUTHENTICATED TBD call from %s\n", ast_inet_ntoa(sin.sin_addr));
11217 if (ast_test_flag64(iaxs[fr->callno], IAX_IMMEDIATE)) {
11218 goto immediatedial;
11219 }
11220 }
11221 }
11222 }
11223 break;
11224 case IAX_COMMAND_DIAL:
11225 immediatedial:
11226 if (ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_TBD)) {
11227 ast_clear_flag(&iaxs[fr->callno]->state, IAX_STATE_TBD);
11228 ast_string_field_set(iaxs[fr->callno], exten, ies.called_number ? ies.called_number : "s");
11229 if (!ast_exists_extension(NULL, iaxs[fr->callno]->context, iaxs[fr->callno]->exten, 1, iaxs[fr->callno]->cid_num)) {
11230 if (authdebug)
11231 ast_log(LOG_NOTICE, "Rejected dial attempt from %s, request '%s@%s' does not exist\n", ast_inet_ntoa(sin.sin_addr), iaxs[fr->callno]->exten, iaxs[fr->callno]->context);
11232 memset(&ied0, 0, sizeof(ied0));
11233 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "No such context/extension");
11234 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_NO_ROUTE_DESTINATION);
11235 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
11236 if (!iaxs[fr->callno]) {
11237 break;
11238 }
11239 } else {
11240 char tmp[256];
11241 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED);
11242 ast_verb(3, "Accepting DIAL from %s, formats = %s\n",
11243 ast_inet_ntoa(sin.sin_addr),
11244 ast_getformatname_multiple(tmp, sizeof(tmp), iaxs[fr->callno]->peerformat));
11245 ast_set_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED);
11246 send_command(iaxs[fr->callno], AST_FRAME_CONTROL, AST_CONTROL_PROGRESS, 0, NULL, 0, -1);
11247 if (!(c = ast_iax2_new(fr->callno, AST_STATE_RING, iaxs[fr->callno]->peerformat, NULL)))
11248 iax2_destroy(fr->callno);
11249 else if (ies.vars) {
11250 struct ast_datastore *variablestore;
11251 struct ast_variable *var, *prev = NULL;
11252 AST_LIST_HEAD(, ast_var_t) *varlist;
11253 varlist = ast_calloc(1, sizeof(*varlist));
11254 variablestore = ast_datastore_alloc(&iax2_variable_datastore_info, NULL);
11255 ast_debug(1, "I can haz IAX vars? w00t\n");
11256 if (variablestore && varlist) {
11257 variablestore->data = varlist;
11258 variablestore->inheritance = DATASTORE_INHERIT_FOREVER;
11259 AST_LIST_HEAD_INIT(varlist);
11260 for (var = ies.vars; var; var = var->next) {
11261 struct ast_var_t *newvar = ast_var_assign(var->name, var->value);
11262 if (prev)
11263 ast_free(prev);
11264 prev = var;
11265 if (!newvar) {
11266
11267 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
11268 } else {
11269 AST_LIST_INSERT_TAIL(varlist, newvar, entries);
11270 }
11271 }
11272 if (prev)
11273 ast_free(prev);
11274 ies.vars = NULL;
11275 ast_channel_datastore_add(c, variablestore);
11276 } else {
11277 ast_log(LOG_ERROR, "Memory allocation error while processing IAX2 variables\n");
11278 if (variablestore)
11279 ast_datastore_free(variablestore);
11280 if (varlist)
11281 ast_free(varlist);
11282 }
11283 }
11284 }
11285 }
11286 break;
11287 case IAX_COMMAND_INVAL:
11288 iaxs[fr->callno]->error = ENOTCONN;
11289 ast_debug(1, "Immediately destroying %d, having received INVAL\n", fr->callno);
11290 iax2_destroy(fr->callno);
11291 ast_debug(1, "Destroying call %d\n", fr->callno);
11292 break;
11293 case IAX_COMMAND_VNAK:
11294 ast_debug(1, "Received VNAK: resending outstanding frames\n");
11295
11296 vnak_retransmit(fr->callno, fr->iseqno);
11297 break;
11298 case IAX_COMMAND_REGREQ:
11299 case IAX_COMMAND_REGREL:
11300
11301 if (delayreject)
11302 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
11303 if (register_verify(fr->callno, &sin, &ies)) {
11304 if (!iaxs[fr->callno]) {
11305 break;
11306 }
11307
11308 auth_fail(fr->callno, IAX_COMMAND_REGREJ);
11309 break;
11310 }
11311 if (!iaxs[fr->callno]) {
11312 break;
11313 }
11314 if ((ast_strlen_zero(iaxs[fr->callno]->secret) && ast_strlen_zero(iaxs[fr->callno]->inkeys)) ||
11315 ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_AUTHENTICATED)) {
11316
11317 if (f.subclass.integer == IAX_COMMAND_REGREL) {
11318 memset(&sin, 0, sizeof(sin));
11319 sin.sin_family = AF_INET;
11320 }
11321 if (update_registry(&sin, fr->callno, ies.devicetype, fd, ies.refresh)) {
11322 ast_log(LOG_WARNING, "Registry error\n");
11323 }
11324 if (!iaxs[fr->callno]) {
11325 break;
11326 }
11327 if (ies.provverpres && ies.serviceident && sin.sin_addr.s_addr) {
11328 ast_mutex_unlock(&iaxsl[fr->callno]);
11329 check_provisioning(&sin, fd, ies.serviceident, ies.provver);
11330 ast_mutex_lock(&iaxsl[fr->callno]);
11331 }
11332 break;
11333 }
11334 registry_authrequest(fr->callno);
11335 break;
11336 case IAX_COMMAND_REGACK:
11337 if (iax2_ack_registry(&ies, &sin, fr->callno))
11338 ast_log(LOG_WARNING, "Registration failure\n");
11339
11340 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
11341 iax2_destroy(fr->callno);
11342 break;
11343 case IAX_COMMAND_REGREJ:
11344 if (iaxs[fr->callno]->reg) {
11345 if (authdebug) {
11346 ast_log(LOG_NOTICE, "Registration of '%s' rejected: '%s' from: '%s'\n", iaxs[fr->callno]->reg->username, ies.cause ? ies.cause : "<unknown>", ast_inet_ntoa(sin.sin_addr));
11347 manager_event(EVENT_FLAG_SYSTEM, "Registry", "ChannelType: IAX2\r\nUsername: %s\r\nStatus: Rejected\r\nCause: %s\r\n", iaxs[fr->callno]->reg->username, ies.cause ? ies.cause : "<unknown>");
11348 }
11349 iaxs[fr->callno]->reg->regstate = REG_STATE_REJECTED;
11350 }
11351
11352 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
11353 iax2_destroy(fr->callno);
11354 break;
11355 case IAX_COMMAND_REGAUTH:
11356
11357 if (registry_rerequest(&ies, fr->callno, &sin)) {
11358 memset(&ied0, 0, sizeof(ied0));
11359 iax_ie_append_str(&ied0, IAX_IE_CAUSE, "No authority found");
11360 iax_ie_append_byte(&ied0, IAX_IE_CAUSECODE, AST_CAUSE_FACILITY_NOT_SUBSCRIBED);
11361 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
11362 }
11363 break;
11364 case IAX_COMMAND_TXREJ:
11365 iaxs[fr->callno]->transferring = 0;
11366 ast_verb(3, "Channel '%s' unable to transfer\n", iaxs[fr->callno]->owner ? iaxs[fr->callno]->owner->name : "<Unknown>");
11367 memset(&iaxs[fr->callno]->transfer, 0, sizeof(iaxs[fr->callno]->transfer));
11368 if (iaxs[fr->callno]->bridgecallno) {
11369 if (iaxs[iaxs[fr->callno]->bridgecallno]->transferring) {
11370 iaxs[iaxs[fr->callno]->bridgecallno]->transferring = 0;
11371 send_command(iaxs[iaxs[fr->callno]->bridgecallno], AST_FRAME_IAX, IAX_COMMAND_TXREJ, 0, NULL, 0, -1);
11372 }
11373 }
11374 break;
11375 case IAX_COMMAND_TXREADY:
11376 if ((iaxs[fr->callno]->transferring == TRANSFER_BEGIN) ||
11377 (iaxs[fr->callno]->transferring == TRANSFER_MBEGIN)) {
11378 if (iaxs[fr->callno]->transferring == TRANSFER_MBEGIN)
11379 iaxs[fr->callno]->transferring = TRANSFER_MREADY;
11380 else
11381 iaxs[fr->callno]->transferring = TRANSFER_READY;
11382 ast_verb(3, "Channel '%s' ready to transfer\n", iaxs[fr->callno]->owner ? iaxs[fr->callno]->owner->name : "<Unknown>");
11383 if (iaxs[fr->callno]->bridgecallno) {
11384 if ((iaxs[iaxs[fr->callno]->bridgecallno]->transferring == TRANSFER_READY) ||
11385 (iaxs[iaxs[fr->callno]->bridgecallno]->transferring == TRANSFER_MREADY)) {
11386
11387 if (iaxs[fr->callno]->transferring == TRANSFER_MREADY) {
11388 ast_verb(3, "Attempting media bridge of %s and %s\n", iaxs[fr->callno]->owner ? iaxs[fr->callno]->owner->name : "<Unknown>",
11389 iaxs[iaxs[fr->callno]->bridgecallno]->owner ? iaxs[iaxs[fr->callno]->bridgecallno]->owner->name : "<Unknown>");
11390
11391 iaxs[iaxs[fr->callno]->bridgecallno]->transferring = TRANSFER_MEDIA;
11392 iaxs[fr->callno]->transferring = TRANSFER_MEDIA;
11393
11394 memset(&ied0, 0, sizeof(ied0));
11395 memset(&ied1, 0, sizeof(ied1));
11396 iax_ie_append_short(&ied0, IAX_IE_CALLNO, iaxs[iaxs[fr->callno]->bridgecallno]->peercallno);
11397 iax_ie_append_short(&ied1, IAX_IE_CALLNO, iaxs[fr->callno]->peercallno);
11398 send_command(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_TXMEDIA, 0, ied0.buf, ied0.pos, -1);
11399 send_command(iaxs[iaxs[fr->callno]->bridgecallno], AST_FRAME_IAX, IAX_COMMAND_TXMEDIA, 0, ied1.buf, ied1.pos, -1);
11400 } else {
11401 ast_verb(3, "Releasing %s and %s\n", iaxs[fr->callno]->owner ? iaxs[fr->callno]->owner->name : "<Unknown>",
11402 iaxs[iaxs[fr->callno]->bridgecallno]->owner ? iaxs[iaxs[fr->callno]->bridgecallno]->owner->name : "<Unknown>");
11403
11404 iaxs[iaxs[fr->callno]->bridgecallno]->transferring = TRANSFER_RELEASED;
11405 iaxs[fr->callno]->transferring = TRANSFER_RELEASED;
11406 ast_set_flag64(iaxs[iaxs[fr->callno]->bridgecallno], IAX_ALREADYGONE);
11407 ast_set_flag64(iaxs[fr->callno], IAX_ALREADYGONE);
11408
11409
11410 stop_stuff(fr->callno);
11411 stop_stuff(iaxs[fr->callno]->bridgecallno);
11412
11413 memset(&ied0, 0, sizeof(ied0));
11414 memset(&ied1, 0, sizeof(ied1));
11415 iax_ie_append_short(&ied0, IAX_IE_CALLNO, iaxs[iaxs[fr->callno]->bridgecallno]->peercallno);
11416 iax_ie_append_short(&ied1, IAX_IE_CALLNO, iaxs[fr->callno]->peercallno);
11417 send_command(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_TXREL, 0, ied0.buf, ied0.pos, -1);
11418 send_command(iaxs[iaxs[fr->callno]->bridgecallno], AST_FRAME_IAX, IAX_COMMAND_TXREL, 0, ied1.buf, ied1.pos, -1);
11419 }
11420
11421 }
11422 }
11423 }
11424 break;
11425 case IAX_COMMAND_TXREQ:
11426 try_transfer(iaxs[fr->callno], &ies);
11427 break;
11428 case IAX_COMMAND_TXCNT:
11429 if (iaxs[fr->callno]->transferring)
11430 send_command_transfer(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_TXACC, 0, NULL, 0);
11431 break;
11432 case IAX_COMMAND_TXREL:
11433
11434 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
11435 complete_transfer(fr->callno, &ies);
11436 stop_stuff(fr->callno);
11437 break;
11438 case IAX_COMMAND_TXMEDIA:
11439 if (iaxs[fr->callno]->transferring == TRANSFER_READY) {
11440 AST_LIST_TRAVERSE(&frame_queue[fr->callno], cur, list) {
11441
11442 if (cur->transfer) {
11443 cur->retries = -1;
11444 }
11445 }
11446
11447 iaxs[fr->callno]->transferring = TRANSFER_MEDIAPASS;
11448 }
11449 break;
11450 case IAX_COMMAND_RTKEY:
11451 if (!IAX_CALLENCRYPTED(iaxs[fr->callno])) {
11452 ast_log(LOG_WARNING,
11453 "we've been told to rotate our encryption key, "
11454 "but this isn't an encrypted call. bad things will happen.\n"
11455 );
11456 break;
11457 }
11458
11459 IAX_DEBUGDIGEST("Receiving", ies.challenge);
11460
11461 ast_aes_set_decrypt_key((unsigned char *) ies.challenge, &iaxs[fr->callno]->dcx);
11462 break;
11463 case IAX_COMMAND_DPREP:
11464 complete_dpreply(iaxs[fr->callno], &ies);
11465 break;
11466 case IAX_COMMAND_UNSUPPORT:
11467 ast_log(LOG_NOTICE, "Peer did not understand our iax command '%d'\n", ies.iax_unknown);
11468 break;
11469 case IAX_COMMAND_FWDOWNL:
11470
11471 if (!ast_test_flag64(&globalflags, IAX_ALLOWFWDOWNLOAD)) {
11472 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_UNSUPPORT, 0, NULL, 0, -1);
11473 break;
11474 }
11475 memset(&ied0, 0, sizeof(ied0));
11476 res = iax_firmware_append(&ied0, (unsigned char *)ies.devicetype, ies.fwdesc);
11477 if (res < 0)
11478 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_REJECT, 0, ied0.buf, ied0.pos, -1);
11479 else if (res > 0)
11480 send_command_final(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_FWDATA, 0, ied0.buf, ied0.pos, -1);
11481 else
11482 send_command(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_FWDATA, 0, ied0.buf, ied0.pos, -1);
11483 break;
11484 case IAX_COMMAND_CALLTOKEN:
11485 {
11486 struct iax_frame *cur;
11487
11488 if ((cur = AST_LIST_LAST(&frame_queue[fr->callno])) && ies.calltoken && ies.calltokendata) {
11489 resend_with_token(fr->callno, cur, (char *) ies.calltokendata);
11490 }
11491 break;
11492 }
11493 default:
11494 ast_debug(1, "Unknown IAX command %d on %d/%d\n", f.subclass.integer, fr->callno, iaxs[fr->callno]->peercallno);
11495 memset(&ied0, 0, sizeof(ied0));
11496 iax_ie_append_byte(&ied0, IAX_IE_IAX_UNKNOWN, f.subclass.integer);
11497 send_command(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_UNSUPPORT, 0, ied0.buf, ied0.pos, -1);
11498 }
11499
11500 if (ies.vars) {
11501 ast_variables_destroy(ies.vars);
11502 ast_debug(1, "I can haz IAX vars, but they is no good :-(\n");
11503 ies.vars = NULL;
11504 }
11505
11506
11507 if ((f.subclass.integer != IAX_COMMAND_ACK) &&
11508 (f.subclass.integer != IAX_COMMAND_TXCNT) &&
11509 (f.subclass.integer != IAX_COMMAND_TXACC) &&
11510 (f.subclass.integer != IAX_COMMAND_INVAL) &&
11511 (f.subclass.integer != IAX_COMMAND_VNAK)) {
11512 if (iaxs[fr->callno] && iaxs[fr->callno]->aseqno != iaxs[fr->callno]->iseqno)
11513 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
11514 }
11515 ast_mutex_unlock(&iaxsl[fr->callno]);
11516 return 1;
11517 }
11518
11519 if (iaxs[fr->callno] && iaxs[fr->callno]->aseqno != iaxs[fr->callno]->iseqno)
11520 send_command_immediate(iaxs[fr->callno], AST_FRAME_IAX, IAX_COMMAND_ACK, fr->ts, NULL, 0,fr->iseqno);
11521 } else if (minivid) {
11522 f.frametype = AST_FRAME_VIDEO;
11523 if (iaxs[fr->callno]->videoformat > 0)
11524 f.subclass.codec = iaxs[fr->callno]->videoformat | (ntohs(vh->ts) & 0x8000LL ? 1 : 0);
11525 else {
11526 ast_log(LOG_WARNING, "Received mini frame before first full video frame\n");
11527 iax2_vnak(fr->callno);
11528 ast_variables_destroy(ies.vars);
11529 ast_mutex_unlock(&iaxsl[fr->callno]);
11530 return 1;
11531 }
11532 f.datalen = res - sizeof(*vh);
11533 if (f.datalen)
11534 f.data.ptr = thread->buf + sizeof(*vh);
11535 else
11536 f.data.ptr = NULL;
11537 #ifdef IAXTESTS
11538 if (test_resync) {
11539 fr->ts = (iaxs[fr->callno]->last & 0xFFFF8000L) | ((ntohs(vh->ts) + test_resync) & 0x7fff);
11540 } else
11541 #endif
11542 fr->ts = (iaxs[fr->callno]->last & 0xFFFF8000L) | (ntohs(vh->ts) & 0x7fff);
11543 } else {
11544
11545 f.frametype = AST_FRAME_VOICE;
11546 if (iaxs[fr->callno]->voiceformat > 0)
11547 f.subclass.codec = iaxs[fr->callno]->voiceformat;
11548 else {
11549 ast_debug(1, "Received mini frame before first full voice frame\n");
11550 iax2_vnak(fr->callno);
11551 ast_variables_destroy(ies.vars);
11552 ast_mutex_unlock(&iaxsl[fr->callno]);
11553 return 1;
11554 }
11555 f.datalen = res - sizeof(struct ast_iax2_mini_hdr);
11556 if (f.datalen < 0) {
11557 ast_log(LOG_WARNING, "Datalen < 0?\n");
11558 ast_variables_destroy(ies.vars);
11559 ast_mutex_unlock(&iaxsl[fr->callno]);
11560 return 1;
11561 }
11562 if (f.datalen)
11563 f.data.ptr = thread->buf + sizeof(*mh);
11564 else
11565 f.data.ptr = NULL;
11566 #ifdef IAXTESTS
11567 if (test_resync) {
11568 fr->ts = (iaxs[fr->callno]->last & 0xFFFF0000L) | ((ntohs(mh->ts) + test_resync) & 0xffff);
11569 } else
11570 #endif
11571 fr->ts = (iaxs[fr->callno]->last & 0xFFFF0000L) | ntohs(mh->ts);
11572
11573 }
11574
11575 if (!ast_test_flag(&iaxs[fr->callno]->state, IAX_STATE_STARTED)) {
11576 ast_variables_destroy(ies.vars);
11577 ast_mutex_unlock(&iaxsl[fr->callno]);
11578 return 1;
11579 }
11580
11581 if (f.frametype == AST_FRAME_CONTROL && f.subclass.integer == AST_CONTROL_CONNECTED_LINE) {
11582 struct ast_party_connected_line connected;
11583
11584 if (!ast_test_flag64(iaxs[fr->callno], IAX_RECVCONNECTEDLINE)) {
11585 ast_variables_destroy(ies.vars);
11586 ast_mutex_unlock(&iaxsl[fr->callno]);
11587 return 1;
11588 }
11589
11590
11591 ast_party_connected_line_init(&connected);
11592 connected.id.number.presentation = iaxs[fr->callno]->calling_pres;
11593 connected.id.name.presentation = iaxs[fr->callno]->calling_pres;
11594
11595 if (!ast_connected_line_parse_data(f.data.ptr, f.datalen, &connected)) {
11596 ast_string_field_set(iaxs[fr->callno], cid_num, connected.id.number.str);
11597 ast_string_field_set(iaxs[fr->callno], cid_name, connected.id.name.str);
11598 iaxs[fr->callno]->calling_pres = ast_party_id_presentation(&connected.id);
11599
11600 if (iaxs[fr->callno]->owner) {
11601 ast_set_callerid(iaxs[fr->callno]->owner,
11602 S_COR(connected.id.number.valid, connected.id.number.str, ""),
11603 S_COR(connected.id.name.valid, connected.id.name.str, ""),
11604 NULL);
11605 iaxs[fr->callno]->owner->caller.id.number.presentation = connected.id.number.presentation;
11606 iaxs[fr->callno]->owner->caller.id.name.presentation = connected.id.name.presentation;
11607 }
11608 }
11609 ast_party_connected_line_free(&connected);
11610 }
11611
11612 f.src = "IAX2";
11613 f.mallocd = 0;
11614 f.offset = 0;
11615 f.len = 0;
11616 if (f.datalen && (f.frametype == AST_FRAME_VOICE)) {
11617 f.samples = ast_codec_get_samples(&f);
11618
11619 if (f.subclass.codec == AST_FORMAT_SLINEAR)
11620 ast_frame_byteswap_be(&f);
11621 } else
11622 f.samples = 0;
11623 iax_frame_wrap(fr, &f);
11624
11625
11626 if (iaxs[fr->callno] && iaxs[fr->callno]->last < fr->ts) {
11627
11628 fr->outoforder = 0;
11629 } else {
11630 if (iaxdebug && iaxs[fr->callno])
11631 ast_debug(1, "Received out of order packet... (type=%d, subclass %d, ts = %d, last = %d)\n", f.frametype, f.subclass.integer, fr->ts, iaxs[fr->callno]->last);
11632 fr->outoforder = -1;
11633 }
11634 fr->cacheable = ((f.frametype == AST_FRAME_VOICE) || (f.frametype == AST_FRAME_VIDEO));
11635 duped_fr = iaxfrdup2(fr);
11636 if (duped_fr) {
11637 schedule_delivery(duped_fr, updatehistory, 0, &fr->ts);
11638 }
11639 if (iaxs[fr->callno] && iaxs[fr->callno]->last < fr->ts) {
11640 iaxs[fr->callno]->last = fr->ts;
11641 #if 1
11642 if (iaxdebug)
11643 ast_debug(1, "For call=%d, set last=%d\n", fr->callno, fr->ts);
11644 #endif
11645 }
11646
11647
11648 ast_variables_destroy(ies.vars);
11649 ast_mutex_unlock(&iaxsl[fr->callno]);
11650 return 1;
11651 }
11652
11653
11654 static void iax2_process_thread_cleanup(void *data)
11655 {
11656 struct iax2_thread *thread = data;
11657 ast_mutex_destroy(&thread->lock);
11658 ast_cond_destroy(&thread->cond);
11659 ast_mutex_destroy(&thread->init_lock);
11660 ast_cond_destroy(&thread->init_cond);
11661 ast_free(thread);
11662
11663 ast_atomic_dec_and_test(&iaxactivethreadcount);
11664 }
11665
11666 static void *iax2_process_thread(void *data)
11667 {
11668 struct iax2_thread *thread = data;
11669 struct timeval wait;
11670 struct timespec ts;
11671 int put_into_idle = 0;
11672 int first_time = 1;
11673 int old_state;
11674
11675 ast_atomic_fetchadd_int(&iaxactivethreadcount, 1);
11676
11677 pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, &old_state);
11678 pthread_cleanup_push(iax2_process_thread_cleanup, data);
11679
11680 for (;;) {
11681
11682 ast_mutex_lock(&thread->lock);
11683
11684 if (thread->stop) {
11685 ast_mutex_unlock(&thread->lock);
11686 break;
11687 }
11688
11689
11690 if (first_time) {
11691 signal_condition(&thread->init_lock, &thread->init_cond);
11692 first_time = 0;
11693 }
11694
11695
11696 if (put_into_idle) {
11697 insert_idle_thread(thread);
11698 }
11699
11700 if (thread->type == IAX_THREAD_TYPE_DYNAMIC) {
11701 struct iax2_thread *t = NULL;
11702
11703 wait = ast_tvadd(ast_tvnow(), ast_samp2tv(30000, 1000));
11704 ts.tv_sec = wait.tv_sec;
11705 ts.tv_nsec = wait.tv_usec * 1000;
11706 if (ast_cond_timedwait(&thread->cond, &thread->lock, &ts) == ETIMEDOUT) {
11707
11708
11709 if (!put_into_idle || thread->stop) {
11710 ast_mutex_unlock(&thread->lock);
11711 break;
11712 }
11713 AST_LIST_LOCK(&dynamic_list);
11714
11715 if ((t = AST_LIST_REMOVE(&dynamic_list, thread, list)))
11716 ast_atomic_fetchadd_int(&iaxdynamicthreadcount, -1);
11717 AST_LIST_UNLOCK(&dynamic_list);
11718 if (t) {
11719
11720
11721
11722 ast_mutex_unlock(&thread->lock);
11723 break;
11724 }
11725
11726
11727
11728 wait = ast_tvadd(ast_tvnow(), ast_samp2tv(30000, 1000));
11729 ts.tv_sec = wait.tv_sec;
11730 ts.tv_nsec = wait.tv_usec * 1000;
11731 if (ast_cond_timedwait(&thread->cond, &thread->lock, &ts) == ETIMEDOUT) {
11732 ast_mutex_unlock(&thread->lock);
11733 break;
11734 }
11735 }
11736 } else {
11737 ast_cond_wait(&thread->cond, &thread->lock);
11738 }
11739
11740
11741 put_into_idle = 1;
11742
11743 ast_mutex_unlock(&thread->lock);
11744
11745 if (thread->stop) {
11746 break;
11747 }
11748
11749 if (thread->iostate == IAX_IOSTATE_IDLE)
11750 continue;
11751
11752
11753 switch (thread->iostate) {
11754 case IAX_IOSTATE_READY:
11755 thread->actions++;
11756 thread->iostate = IAX_IOSTATE_PROCESSING;
11757 socket_process(thread);
11758 handle_deferred_full_frames(thread);
11759 break;
11760 case IAX_IOSTATE_SCHEDREADY:
11761 thread->actions++;
11762 thread->iostate = IAX_IOSTATE_PROCESSING;
11763 #ifdef SCHED_MULTITHREADED
11764 thread->schedfunc(thread->scheddata);
11765 #endif
11766 default:
11767 break;
11768 }
11769 time(&thread->checktime);
11770 thread->iostate = IAX_IOSTATE_IDLE;
11771 #ifdef DEBUG_SCHED_MULTITHREAD
11772 thread->curfunc[0]='\0';
11773 #endif
11774
11775
11776
11777
11778 AST_LIST_LOCK(&active_list);
11779 AST_LIST_REMOVE(&active_list, thread, list);
11780 AST_LIST_UNLOCK(&active_list);
11781
11782
11783 handle_deferred_full_frames(thread);
11784 }
11785
11786
11787
11788
11789
11790
11791 AST_LIST_LOCK(&idle_list);
11792 AST_LIST_REMOVE(&idle_list, thread, list);
11793 AST_LIST_UNLOCK(&idle_list);
11794
11795 AST_LIST_LOCK(&dynamic_list);
11796 AST_LIST_REMOVE(&dynamic_list, thread, list);
11797 AST_LIST_UNLOCK(&dynamic_list);
11798
11799 if (!thread->stop) {
11800
11801 pthread_detach(pthread_self());
11802 }
11803
11804
11805
11806
11807 pthread_cleanup_pop(1);
11808 return NULL;
11809 }
11810
11811 static int iax2_do_register(struct iax2_registry *reg)
11812 {
11813 struct iax_ie_data ied;
11814 if (iaxdebug)
11815 ast_debug(1, "Sending registration request for '%s'\n", reg->username);
11816
11817 if (reg->dnsmgr &&
11818 ((reg->regstate == REG_STATE_TIMEOUT) || !ast_sockaddr_ipv4(®->addr))) {
11819
11820 ast_dnsmgr_refresh(reg->dnsmgr);
11821 }
11822
11823
11824
11825
11826
11827 if (reg->dnsmgr && ast_dnsmgr_changed(reg->dnsmgr) && (reg->callno > 0)) {
11828 int callno = reg->callno;
11829 ast_mutex_lock(&iaxsl[callno]);
11830 iax2_destroy(callno);
11831 ast_mutex_unlock(&iaxsl[callno]);
11832 reg->callno = 0;
11833 }
11834 if (!ast_sockaddr_ipv4(®->addr)) {
11835 if (iaxdebug)
11836 ast_debug(1, "Unable to send registration request for '%s' without IP address\n", reg->username);
11837
11838 reg->expire = iax2_sched_replace(reg->expire, sched,
11839 (5 * reg->refresh / 6) * 1000, iax2_do_register_s, reg);
11840 return -1;
11841 }
11842
11843 if (!reg->callno) {
11844 struct sockaddr_in reg_addr;
11845
11846 ast_debug(3, "Allocate call number\n");
11847
11848 ast_sockaddr_to_sin(®->addr, ®_addr);
11849
11850 reg->callno = find_callno_locked(0, 0, ®_addr, NEW_FORCE, defaultsockfd, 0);
11851 if (reg->callno < 1) {
11852 ast_log(LOG_WARNING, "Unable to create call for registration\n");
11853 return -1;
11854 } else
11855 ast_debug(3, "Registration created on call %d\n", reg->callno);
11856 iaxs[reg->callno]->reg = reg;
11857 ast_mutex_unlock(&iaxsl[reg->callno]);
11858 }
11859
11860 reg->expire = iax2_sched_replace(reg->expire, sched,
11861 (5 * reg->refresh / 6) * 1000, iax2_do_register_s, reg);
11862
11863 memset(&ied, 0, sizeof(ied));
11864 iax_ie_append_str(&ied, IAX_IE_USERNAME, reg->username);
11865 iax_ie_append_short(&ied, IAX_IE_REFRESH, reg->refresh);
11866 add_empty_calltoken_ie(iaxs[reg->callno], &ied);
11867 send_command(iaxs[reg->callno],AST_FRAME_IAX, IAX_COMMAND_REGREQ, 0, ied.buf, ied.pos, -1);
11868 reg->regstate = REG_STATE_REGSENT;
11869 return 0;
11870 }
11871
11872 static int iax2_provision(struct sockaddr_in *end, int sockfd, const char *dest, const char *template, int force)
11873 {
11874
11875
11876 struct iax_ie_data provdata;
11877 struct iax_ie_data ied;
11878 unsigned int sig;
11879 struct sockaddr_in sin;
11880 int callno;
11881 struct create_addr_info cai;
11882
11883 memset(&cai, 0, sizeof(cai));
11884
11885 ast_debug(1, "Provisioning '%s' from template '%s'\n", dest, template);
11886
11887 if (iax_provision_build(&provdata, &sig, template, force)) {
11888 ast_debug(1, "No provisioning found for template '%s'\n", template);
11889 return 0;
11890 }
11891
11892 if (end) {
11893 memcpy(&sin, end, sizeof(sin));
11894 cai.sockfd = sockfd;
11895 } else if (create_addr(dest, NULL, &sin, &cai))
11896 return -1;
11897
11898
11899 memset(&ied, 0, sizeof(ied));
11900 iax_ie_append_raw(&ied, IAX_IE_PROVISIONING, provdata.buf, provdata.pos);
11901
11902 callno = find_callno_locked(0, 0, &sin, NEW_FORCE, cai.sockfd, 0);
11903 if (!callno)
11904 return -1;
11905
11906 if (iaxs[callno]) {
11907
11908 iaxs[callno]->autoid = iax2_sched_replace(iaxs[callno]->autoid,
11909 sched, 15000, auto_hangup, (void *)(long)callno);
11910 ast_set_flag64(iaxs[callno], IAX_PROVISION);
11911
11912 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_PROVISION, 0, ied.buf, ied.pos, -1);
11913 }
11914 ast_mutex_unlock(&iaxsl[callno]);
11915
11916 return 1;
11917 }
11918
11919 static char *papp = "IAX2Provision";
11920
11921
11922
11923
11924 static int iax2_prov_app(struct ast_channel *chan, const char *data)
11925 {
11926 int res;
11927 char *sdata;
11928 char *opts;
11929 int force =0;
11930 unsigned short callno = PTR_TO_CALLNO(chan->tech_pvt);
11931 if (ast_strlen_zero(data))
11932 data = "default";
11933 sdata = ast_strdupa(data);
11934 opts = strchr(sdata, '|');
11935 if (opts)
11936 *opts='\0';
11937
11938 if (chan->tech != &iax2_tech) {
11939 ast_log(LOG_NOTICE, "Can't provision a non-IAX device!\n");
11940 return -1;
11941 }
11942 if (!callno || !iaxs[callno] || !iaxs[callno]->addr.sin_addr.s_addr) {
11943 ast_log(LOG_NOTICE, "Can't provision something with no IP?\n");
11944 return -1;
11945 }
11946 res = iax2_provision(&iaxs[callno]->addr, iaxs[callno]->sockfd, NULL, sdata, force);
11947 ast_verb(3, "Provisioned IAXY at '%s' with '%s'= %d\n",
11948 ast_inet_ntoa(iaxs[callno]->addr.sin_addr),
11949 sdata, res);
11950 return res;
11951 }
11952
11953 static char *handle_cli_iax2_provision(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
11954 {
11955 int force = 0;
11956 int res;
11957
11958 switch (cmd) {
11959 case CLI_INIT:
11960 e->command = "iax2 provision";
11961 e->usage =
11962 "Usage: iax2 provision <host> <template> [forced]\n"
11963 " Provisions the given peer or IP address using a template\n"
11964 " matching either 'template' or '*' if the template is not\n"
11965 " found. If 'forced' is specified, even empty provisioning\n"
11966 " fields will be provisioned as empty fields.\n";
11967 return NULL;
11968 case CLI_GENERATE:
11969 if (a->pos == 3)
11970 return iax_prov_complete_template(a->line, a->word, a->pos, a->n);
11971 return NULL;
11972 }
11973
11974 if (a->argc < 4)
11975 return CLI_SHOWUSAGE;
11976 if (a->argc > 4) {
11977 if (!strcasecmp(a->argv[4], "forced"))
11978 force = 1;
11979 else
11980 return CLI_SHOWUSAGE;
11981 }
11982 res = iax2_provision(NULL, -1, a->argv[2], a->argv[3], force);
11983 if (res < 0)
11984 ast_cli(a->fd, "Unable to find peer/address '%s'\n", a->argv[2]);
11985 else if (res < 1)
11986 ast_cli(a->fd, "No template (including wildcard) matching '%s'\n", a->argv[3]);
11987 else
11988 ast_cli(a->fd, "Provisioning '%s' with template '%s'%s\n", a->argv[2], a->argv[3], force ? ", forced" : "");
11989 return CLI_SUCCESS;
11990 }
11991
11992 static void __iax2_poke_noanswer(const void *data)
11993 {
11994 struct iax2_peer *peer = (struct iax2_peer *)data;
11995 int callno;
11996
11997 if (peer->lastms > -1) {
11998 ast_log(LOG_NOTICE, "Peer '%s' is now UNREACHABLE! Time: %d\n", peer->name, peer->lastms);
11999 manager_event(EVENT_FLAG_SYSTEM, "PeerStatus", "ChannelType: IAX2\r\nPeer: IAX2/%s\r\nPeerStatus: Unreachable\r\nTime: %d\r\n", peer->name, peer->lastms);
12000 ast_devstate_changed(AST_DEVICE_UNAVAILABLE, "IAX2/%s", peer->name);
12001 }
12002 if ((callno = peer->callno) > 0) {
12003 ast_mutex_lock(&iaxsl[callno]);
12004 iax2_destroy(callno);
12005 ast_mutex_unlock(&iaxsl[callno]);
12006 }
12007 peer->callno = 0;
12008 peer->lastms = -1;
12009
12010 peer->pokeexpire = iax2_sched_add(sched, peer->pokefreqnotok, iax2_poke_peer_s, peer_ref(peer));
12011 if (peer->pokeexpire == -1)
12012 peer_unref(peer);
12013 }
12014
12015 static int iax2_poke_noanswer(const void *data)
12016 {
12017 struct iax2_peer *peer = (struct iax2_peer *)data;
12018 peer->pokeexpire = -1;
12019 #ifdef SCHED_MULTITHREADED
12020 if (schedule_action(__iax2_poke_noanswer, data))
12021 #endif
12022 __iax2_poke_noanswer(data);
12023 peer_unref(peer);
12024 return 0;
12025 }
12026
12027 static int iax2_poke_peer_cb(void *obj, void *arg, int flags)
12028 {
12029 struct iax2_peer *peer = obj;
12030
12031 iax2_poke_peer(peer, 0);
12032
12033 return 0;
12034 }
12035
12036 static int iax2_poke_peer(struct iax2_peer *peer, int heldcall)
12037 {
12038 int callno;
12039 struct sockaddr_in peer_addr;
12040
12041 if (!peer->maxms || (!ast_sockaddr_ipv4(&peer->addr) && !peer->dnsmgr)) {
12042
12043
12044 peer->lastms = 0;
12045 peer->historicms = 0;
12046 peer->pokeexpire = -1;
12047 peer->callno = 0;
12048 return 0;
12049 }
12050
12051 ast_sockaddr_to_sin(&peer->addr, &peer_addr);
12052
12053
12054 if ((callno = peer->callno) > 0) {
12055 ast_log(LOG_NOTICE, "Still have a callno...\n");
12056 ast_mutex_lock(&iaxsl[callno]);
12057 iax2_destroy(callno);
12058 ast_mutex_unlock(&iaxsl[callno]);
12059 }
12060 if (heldcall)
12061 ast_mutex_unlock(&iaxsl[heldcall]);
12062 callno = peer->callno = find_callno(0, 0, &peer_addr, NEW_FORCE, peer->sockfd, 0);
12063 if (heldcall)
12064 ast_mutex_lock(&iaxsl[heldcall]);
12065 if (peer->callno < 1) {
12066 ast_log(LOG_WARNING, "Unable to allocate call for poking peer '%s'\n", peer->name);
12067 return -1;
12068 }
12069
12070
12071 iaxs[peer->callno]->pingtime = peer->maxms / 4 + 1;
12072 iaxs[peer->callno]->peerpoke = peer;
12073
12074 if (peer->pokeexpire > -1) {
12075 if (!ast_sched_thread_del(sched, peer->pokeexpire)) {
12076 peer->pokeexpire = -1;
12077 peer_unref(peer);
12078 }
12079 }
12080
12081
12082
12083 if (peer->lastms < 0)
12084 peer->pokeexpire = iax2_sched_add(sched, peer->pokefreqnotok, iax2_poke_noanswer, peer_ref(peer));
12085 else
12086 peer->pokeexpire = iax2_sched_add(sched, DEFAULT_MAXMS * 2, iax2_poke_noanswer, peer_ref(peer));
12087
12088 if (peer->pokeexpire == -1)
12089 peer_unref(peer);
12090
12091
12092 ast_mutex_lock(&iaxsl[callno]);
12093 if (iaxs[callno]) {
12094 struct iax_ie_data ied = {
12095 .buf = { 0 },
12096 .pos = 0,
12097 };
12098 add_empty_calltoken_ie(iaxs[callno], &ied);
12099 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_POKE, 0, ied.buf, ied.pos, -1);
12100 }
12101 ast_mutex_unlock(&iaxsl[callno]);
12102
12103 return 0;
12104 }
12105
12106 static void free_context(struct iax2_context *con)
12107 {
12108 struct iax2_context *conl;
12109 while(con) {
12110 conl = con;
12111 con = con->next;
12112 ast_free(conl);
12113 }
12114 }
12115
12116 static struct ast_channel *iax2_request(const char *type, format_t format, const struct ast_channel *requestor, void *data, int *cause)
12117 {
12118 int callno;
12119 int res;
12120 format_t fmt, native;
12121 struct sockaddr_in sin;
12122 struct ast_channel *c;
12123 struct parsed_dial_string pds;
12124 struct create_addr_info cai;
12125 char *tmpstr;
12126
12127 memset(&pds, 0, sizeof(pds));
12128 tmpstr = ast_strdupa(data);
12129 parse_dial_string(tmpstr, &pds);
12130
12131 if (ast_strlen_zero(pds.peer)) {
12132 ast_log(LOG_WARNING, "No peer provided in the IAX2 dial string '%s'\n", (char *) data);
12133 return NULL;
12134 }
12135
12136 memset(&cai, 0, sizeof(cai));
12137 cai.capability = iax2_capability;
12138
12139 ast_copy_flags64(&cai, &globalflags, IAX_NOTRANSFER | IAX_TRANSFERMEDIA | IAX_USEJITTERBUF | IAX_FORCEJITTERBUF | IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
12140
12141
12142 if (create_addr(pds.peer, NULL, &sin, &cai)) {
12143 *cause = AST_CAUSE_UNREGISTERED;
12144 return NULL;
12145 }
12146
12147 if (pds.port)
12148 sin.sin_port = htons(atoi(pds.port));
12149
12150 callno = find_callno_locked(0, 0, &sin, NEW_FORCE, cai.sockfd, 0);
12151 if (callno < 1) {
12152 ast_log(LOG_WARNING, "Unable to create call\n");
12153 *cause = AST_CAUSE_CONGESTION;
12154 return NULL;
12155 }
12156
12157
12158 ast_copy_flags64(iaxs[callno], &cai, IAX_TRUNK | IAX_SENDANI | IAX_NOTRANSFER | IAX_TRANSFERMEDIA | IAX_USEJITTERBUF | IAX_FORCEJITTERBUF | IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
12159 if (ast_test_flag64(&cai, IAX_TRUNK)) {
12160 int new_callno;
12161 if ((new_callno = make_trunk(callno, 1)) != -1)
12162 callno = new_callno;
12163 }
12164 iaxs[callno]->maxtime = cai.maxtime;
12165 if (cai.found)
12166 ast_string_field_set(iaxs[callno], host, pds.peer);
12167
12168 c = ast_iax2_new(callno, AST_STATE_DOWN, cai.capability, requestor ? requestor->linkedid : NULL);
12169
12170 ast_mutex_unlock(&iaxsl[callno]);
12171
12172 if (c) {
12173
12174 if (c->nativeformats & format)
12175 c->nativeformats &= format;
12176 else {
12177 native = c->nativeformats;
12178 fmt = format;
12179 res = ast_translator_best_choice(&fmt, &native);
12180 if (res < 0) {
12181 ast_log(LOG_WARNING, "Unable to create translator path for %s to %s on %s\n",
12182 ast_getformatname(c->nativeformats), ast_getformatname(fmt), c->name);
12183 ast_hangup(c);
12184 return NULL;
12185 }
12186 c->nativeformats = native;
12187 }
12188 c->readformat = ast_best_codec(c->nativeformats);
12189 c->writeformat = c->readformat;
12190 }
12191
12192 return c;
12193 }
12194
12195 static void *network_thread(void *ignore)
12196 {
12197 if (timer) {
12198 ast_io_add(io, ast_timer_fd(timer), timing_read, AST_IO_IN | AST_IO_PRI, NULL);
12199 }
12200
12201 for (;;) {
12202 pthread_testcancel();
12203
12204
12205
12206 ast_io_wait(io, 1000);
12207 }
12208
12209 return NULL;
12210 }
12211
12212 static int start_network_thread(void)
12213 {
12214 struct iax2_thread *thread;
12215 int threadcount = 0;
12216 int x;
12217 for (x = 0; x < iaxthreadcount; x++) {
12218 thread = ast_calloc(1, sizeof(*thread));
12219 if (thread) {
12220 thread->type = IAX_THREAD_TYPE_POOL;
12221 thread->threadnum = ++threadcount;
12222 ast_mutex_init(&thread->lock);
12223 ast_cond_init(&thread->cond, NULL);
12224 ast_mutex_init(&thread->init_lock);
12225 ast_cond_init(&thread->init_cond, NULL);
12226 if (ast_pthread_create_background(&thread->threadid, NULL, iax2_process_thread, thread)) {
12227 ast_log(LOG_WARNING, "Failed to create new thread!\n");
12228 ast_mutex_destroy(&thread->lock);
12229 ast_cond_destroy(&thread->cond);
12230 ast_mutex_destroy(&thread->init_lock);
12231 ast_cond_destroy(&thread->init_cond);
12232 ast_free(thread);
12233 thread = NULL;
12234 continue;
12235 }
12236 AST_LIST_LOCK(&idle_list);
12237 AST_LIST_INSERT_TAIL(&idle_list, thread, list);
12238 AST_LIST_UNLOCK(&idle_list);
12239 }
12240 }
12241 if (ast_pthread_create_background(&netthreadid, NULL, network_thread, NULL)) {
12242 ast_log(LOG_ERROR, "Failed to create new thread!\n");
12243 return -1;
12244 }
12245 ast_verb(2, "%d helper threads started\n", threadcount);
12246 return 0;
12247 }
12248
12249 static struct iax2_context *build_context(const char *context)
12250 {
12251 struct iax2_context *con;
12252
12253 if ((con = ast_calloc(1, sizeof(*con))))
12254 ast_copy_string(con->context, context, sizeof(con->context));
12255
12256 return con;
12257 }
12258
12259 static int get_auth_methods(const char *value)
12260 {
12261 int methods = 0;
12262 if (strstr(value, "rsa"))
12263 methods |= IAX_AUTH_RSA;
12264 if (strstr(value, "md5"))
12265 methods |= IAX_AUTH_MD5;
12266 if (strstr(value, "plaintext"))
12267 methods |= IAX_AUTH_PLAINTEXT;
12268 return methods;
12269 }
12270
12271
12272
12273
12274
12275 static int check_srcaddr(struct sockaddr *sa, socklen_t salen)
12276 {
12277 int sd;
12278 int res;
12279
12280 sd = socket(AF_INET, SOCK_DGRAM, 0);
12281 if (sd < 0) {
12282 ast_log(LOG_ERROR, "Socket: %s\n", strerror(errno));
12283 return -1;
12284 }
12285
12286 res = bind(sd, sa, salen);
12287 if (res < 0) {
12288 ast_debug(1, "Can't bind: %s\n", strerror(errno));
12289 close(sd);
12290 return 1;
12291 }
12292
12293 close(sd);
12294 return 0;
12295 }
12296
12297
12298
12299
12300 static int peer_set_srcaddr(struct iax2_peer *peer, const char *srcaddr)
12301 {
12302 struct sockaddr_in sin;
12303 struct ast_sockaddr sin_tmp;
12304 int nonlocal = 1;
12305 int port = IAX_DEFAULT_PORTNO;
12306 int sockfd = defaultsockfd;
12307 char *tmp;
12308 char *addr;
12309 char *portstr;
12310
12311 if (!(tmp = ast_strdupa(srcaddr)))
12312 return -1;
12313
12314 addr = strsep(&tmp, ":");
12315 portstr = tmp;
12316
12317 if (portstr) {
12318 port = atoi(portstr);
12319 if (port < 1)
12320 port = IAX_DEFAULT_PORTNO;
12321 }
12322
12323 sin_tmp.ss.ss_family = AF_INET;
12324 if (!ast_get_ip(&sin_tmp, addr)) {
12325 struct ast_netsock *sock;
12326 int res;
12327
12328 ast_sockaddr_to_sin(&sin_tmp, &sin);
12329 sin.sin_port = 0;
12330 sin.sin_family = AF_INET;
12331 res = check_srcaddr((struct sockaddr *) &sin, sizeof(sin));
12332 if (res == 0) {
12333
12334 sin.sin_port = htons(port);
12335 if (!(sock = ast_netsock_find(netsock, &sin)))
12336 sock = ast_netsock_find(outsock, &sin);
12337 if (sock) {
12338 sockfd = ast_netsock_sockfd(sock);
12339 nonlocal = 0;
12340 } else {
12341 unsigned int orig_saddr = sin.sin_addr.s_addr;
12342
12343 sin.sin_addr.s_addr = INADDR_ANY;
12344 if (ast_netsock_find(netsock, &sin)) {
12345 sin.sin_addr.s_addr = orig_saddr;
12346 sock = ast_netsock_bind(outsock, io, srcaddr, port, qos.tos, qos.cos, socket_read, NULL);
12347 if (sock) {
12348 sockfd = ast_netsock_sockfd(sock);
12349 ast_netsock_unref(sock);
12350 nonlocal = 0;
12351 } else {
12352 nonlocal = 2;
12353 }
12354 }
12355 }
12356 }
12357 }
12358
12359 peer->sockfd = sockfd;
12360
12361 if (nonlocal == 1) {
12362 ast_log(LOG_WARNING, "Non-local or unbound address specified (%s) in sourceaddress for '%s', reverting to default\n",
12363 srcaddr, peer->name);
12364 return -1;
12365 } else if (nonlocal == 2) {
12366 ast_log(LOG_WARNING, "Unable to bind to sourceaddress '%s' for '%s', reverting to default\n",
12367 srcaddr, peer->name);
12368 return -1;
12369 } else {
12370 ast_debug(1, "Using sourceaddress %s for '%s'\n", srcaddr, peer->name);
12371 return 0;
12372 }
12373 }
12374
12375 static void peer_destructor(void *obj)
12376 {
12377 struct iax2_peer *peer = obj;
12378 int callno = peer->callno;
12379
12380 ast_free_ha(peer->ha);
12381
12382 if (callno > 0) {
12383 ast_mutex_lock(&iaxsl[callno]);
12384 iax2_destroy(callno);
12385 ast_mutex_unlock(&iaxsl[callno]);
12386 }
12387
12388 register_peer_exten(peer, 0);
12389
12390 if (peer->dnsmgr)
12391 ast_dnsmgr_release(peer->dnsmgr);
12392
12393 if (peer->mwi_event_sub)
12394 ast_event_unsubscribe(peer->mwi_event_sub);
12395
12396 ast_string_field_free_memory(peer);
12397 }
12398
12399
12400 static struct iax2_peer *build_peer(const char *name, struct ast_variable *v, struct ast_variable *alt, int temponly)
12401 {
12402 struct iax2_peer *peer = NULL;
12403 struct ast_ha *oldha = NULL;
12404 int maskfound = 0;
12405 int found = 0;
12406 int firstpass = 1;
12407 struct iax2_peer tmp_peer = {
12408 .name = name,
12409 };
12410
12411 if (!temponly) {
12412 peer = ao2_find(peers, &tmp_peer, OBJ_POINTER);
12413 if (peer && !ast_test_flag64(peer, IAX_DELME))
12414 firstpass = 0;
12415 }
12416
12417 if (peer) {
12418 found++;
12419 if (firstpass) {
12420 oldha = peer->ha;
12421 peer->ha = NULL;
12422 }
12423 unlink_peer(peer);
12424 } else if ((peer = ao2_alloc(sizeof(*peer), peer_destructor))) {
12425 peer->expire = -1;
12426 peer->pokeexpire = -1;
12427 peer->sockfd = defaultsockfd;
12428 peer->addr.ss.ss_family = AF_INET;
12429 peer->addr.len = sizeof(struct sockaddr_in);
12430 if (ast_string_field_init(peer, 32))
12431 peer = peer_unref(peer);
12432 }
12433
12434 if (peer) {
12435 if (firstpass) {
12436 ast_copy_flags64(peer, &globalflags, IAX_USEJITTERBUF | IAX_FORCEJITTERBUF | IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE | IAX_FORCE_ENCRYPT);
12437 peer->encmethods = iax2_encryption;
12438 peer->adsi = adsi;
12439 ast_string_field_set(peer,secret,"");
12440 if (!found) {
12441 ast_string_field_set(peer, name, name);
12442 ast_sockaddr_set_port(&peer->addr, IAX_DEFAULT_PORTNO);
12443 peer->expiry = min_reg_expire;
12444 }
12445 peer->prefs = prefs;
12446 peer->capability = iax2_capability;
12447 peer->smoothing = 0;
12448 peer->pokefreqok = DEFAULT_FREQ_OK;
12449 peer->pokefreqnotok = DEFAULT_FREQ_NOTOK;
12450 peer->maxcallno = 0;
12451 peercnt_modify(0, 0, &peer->addr);
12452 peer->calltoken_required = CALLTOKEN_DEFAULT;
12453 ast_string_field_set(peer,context,"");
12454 ast_string_field_set(peer,peercontext,"");
12455 ast_clear_flag64(peer, IAX_HASCALLERID);
12456 ast_string_field_set(peer, cid_name, "");
12457 ast_string_field_set(peer, cid_num, "");
12458 ast_string_field_set(peer, mohinterpret, mohinterpret);
12459 ast_string_field_set(peer, mohsuggest, mohsuggest);
12460 }
12461
12462 if (!v) {
12463 v = alt;
12464 alt = NULL;
12465 }
12466 while(v) {
12467 if (!strcasecmp(v->name, "secret")) {
12468 ast_string_field_set(peer, secret, v->value);
12469 } else if (!strcasecmp(v->name, "mailbox")) {
12470 ast_string_field_set(peer, mailbox, v->value);
12471 } else if (!strcasecmp(v->name, "hasvoicemail")) {
12472 if (ast_true(v->value) && ast_strlen_zero(peer->mailbox)) {
12473 ast_string_field_set(peer, mailbox, name);
12474 }
12475 } else if (!strcasecmp(v->name, "mohinterpret")) {
12476 ast_string_field_set(peer, mohinterpret, v->value);
12477 } else if (!strcasecmp(v->name, "mohsuggest")) {
12478 ast_string_field_set(peer, mohsuggest, v->value);
12479 } else if (!strcasecmp(v->name, "dbsecret")) {
12480 ast_string_field_set(peer, dbsecret, v->value);
12481 } else if (!strcasecmp(v->name, "trunk")) {
12482 ast_set2_flag64(peer, ast_true(v->value), IAX_TRUNK);
12483 if (ast_test_flag64(peer, IAX_TRUNK) && !timer) {
12484 ast_log(LOG_WARNING, "Unable to support trunking on peer '%s' without a timing interface\n", peer->name);
12485 ast_clear_flag64(peer, IAX_TRUNK);
12486 }
12487 } else if (!strcasecmp(v->name, "auth")) {
12488 peer->authmethods = get_auth_methods(v->value);
12489 } else if (!strcasecmp(v->name, "encryption")) {
12490 peer->encmethods |= get_encrypt_methods(v->value);
12491 if (!peer->encmethods) {
12492 ast_clear_flag64(peer, IAX_FORCE_ENCRYPT);
12493 }
12494 } else if (!strcasecmp(v->name, "forceencryption")) {
12495 if (ast_false(v->value)) {
12496 ast_clear_flag64(peer, IAX_FORCE_ENCRYPT);
12497 } else {
12498 peer->encmethods |= get_encrypt_methods(v->value);
12499 if (peer->encmethods) {
12500 ast_set_flag64(peer, IAX_FORCE_ENCRYPT);
12501 }
12502 }
12503 } else if (!strcasecmp(v->name, "transfer")) {
12504 if (!strcasecmp(v->value, "mediaonly")) {
12505 ast_set_flags_to64(peer, IAX_NOTRANSFER|IAX_TRANSFERMEDIA, IAX_TRANSFERMEDIA);
12506 } else if (ast_true(v->value)) {
12507 ast_set_flags_to64(peer, IAX_NOTRANSFER|IAX_TRANSFERMEDIA, 0);
12508 } else
12509 ast_set_flags_to64(peer, IAX_NOTRANSFER|IAX_TRANSFERMEDIA, IAX_NOTRANSFER);
12510 } else if (!strcasecmp(v->name, "jitterbuffer")) {
12511 ast_set2_flag64(peer, ast_true(v->value), IAX_USEJITTERBUF);
12512 } else if (!strcasecmp(v->name, "forcejitterbuffer")) {
12513 ast_set2_flag64(peer, ast_true(v->value), IAX_FORCEJITTERBUF);
12514 } else if (!strcasecmp(v->name, "host")) {
12515 if (!strcasecmp(v->value, "dynamic")) {
12516
12517 ast_set_flag64(peer, IAX_DYNAMIC);
12518 if (!found) {
12519
12520
12521 if (ast_sockaddr_port(&peer->addr)) {
12522 peer->defaddr.sin_port = htons(ast_sockaddr_port(&peer->addr));
12523 }
12524 ast_sockaddr_setnull(&peer->addr);
12525 }
12526 } else {
12527
12528 ast_sched_thread_del(sched, peer->expire);
12529 ast_clear_flag64(peer, IAX_DYNAMIC);
12530 if (ast_dnsmgr_lookup(v->value, &peer->addr, &peer->dnsmgr, srvlookup ? "_iax._udp" : NULL))
12531 return peer_unref(peer);
12532 if (!ast_sockaddr_port(&peer->addr)) {
12533 ast_sockaddr_set_port(&peer->addr, IAX_DEFAULT_PORTNO);
12534 }
12535 }
12536 if (!maskfound)
12537 inet_aton("255.255.255.255", &peer->mask);
12538 } else if (!strcasecmp(v->name, "defaultip")) {
12539 struct ast_sockaddr peer_defaddr_tmp;
12540
12541 peer_defaddr_tmp.ss.ss_family = AF_INET;
12542 if (ast_get_ip(&peer_defaddr_tmp, v->value)) {
12543 return peer_unref(peer);
12544 }
12545 ast_sockaddr_to_sin(&peer_defaddr_tmp,
12546 &peer->defaddr);
12547 } else if (!strcasecmp(v->name, "sourceaddress")) {
12548 peer_set_srcaddr(peer, v->value);
12549 } else if (!strcasecmp(v->name, "permit") ||
12550 !strcasecmp(v->name, "deny")) {
12551 peer->ha = ast_append_ha(v->name, v->value, peer->ha, NULL);
12552 } else if (!strcasecmp(v->name, "mask")) {
12553 maskfound++;
12554 inet_aton(v->value, &peer->mask);
12555 } else if (!strcasecmp(v->name, "context")) {
12556 ast_string_field_set(peer, context, v->value);
12557 } else if (!strcasecmp(v->name, "regexten")) {
12558 ast_string_field_set(peer, regexten, v->value);
12559 } else if (!strcasecmp(v->name, "peercontext")) {
12560 ast_string_field_set(peer, peercontext, v->value);
12561 } else if (!strcasecmp(v->name, "port")) {
12562 if (ast_test_flag64(peer, IAX_DYNAMIC)) {
12563 peer->defaddr.sin_port = htons(atoi(v->value));
12564 } else {
12565 ast_sockaddr_set_port(&peer->addr, atoi(v->value));
12566 }
12567 } else if (!strcasecmp(v->name, "username")) {
12568 ast_string_field_set(peer, username, v->value);
12569 } else if (!strcasecmp(v->name, "allow")) {
12570 ast_parse_allow_disallow(&peer->prefs, &peer->capability, v->value, 1);
12571 } else if (!strcasecmp(v->name, "disallow")) {
12572 ast_parse_allow_disallow(&peer->prefs, &peer->capability, v->value, 0);
12573 } else if (!strcasecmp(v->name, "callerid")) {
12574 if (!ast_strlen_zero(v->value)) {
12575 char name2[80];
12576 char num2[80];
12577 ast_callerid_split(v->value, name2, sizeof(name2), num2, sizeof(num2));
12578 ast_string_field_set(peer, cid_name, name2);
12579 ast_string_field_set(peer, cid_num, num2);
12580 } else {
12581 ast_string_field_set(peer, cid_name, "");
12582 ast_string_field_set(peer, cid_num, "");
12583 }
12584 ast_set_flag64(peer, IAX_HASCALLERID);
12585 } else if (!strcasecmp(v->name, "fullname")) {
12586 ast_string_field_set(peer, cid_name, S_OR(v->value, ""));
12587 ast_set_flag64(peer, IAX_HASCALLERID);
12588 } else if (!strcasecmp(v->name, "cid_number")) {
12589 ast_string_field_set(peer, cid_num, S_OR(v->value, ""));
12590 ast_set_flag64(peer, IAX_HASCALLERID);
12591 } else if (!strcasecmp(v->name, "sendani")) {
12592 ast_set2_flag64(peer, ast_true(v->value), IAX_SENDANI);
12593 } else if (!strcasecmp(v->name, "inkeys")) {
12594 ast_string_field_set(peer, inkeys, v->value);
12595 } else if (!strcasecmp(v->name, "outkey")) {
12596 ast_string_field_set(peer, outkey, v->value);
12597 } else if (!strcasecmp(v->name, "qualify")) {
12598 if (!strcasecmp(v->value, "no")) {
12599 peer->maxms = 0;
12600 } else if (!strcasecmp(v->value, "yes")) {
12601 peer->maxms = DEFAULT_MAXMS;
12602 } else if (sscanf(v->value, "%30d", &peer->maxms) != 1) {
12603 ast_log(LOG_WARNING, "Qualification of peer '%s' should be 'yes', 'no', or a number of milliseconds at line %d of iax.conf\n", peer->name, v->lineno);
12604 peer->maxms = 0;
12605 }
12606 } else if (!strcasecmp(v->name, "qualifysmoothing")) {
12607 peer->smoothing = ast_true(v->value);
12608 } else if (!strcasecmp(v->name, "qualifyfreqok")) {
12609 if (sscanf(v->value, "%30d", &peer->pokefreqok) != 1) {
12610 ast_log(LOG_WARNING, "Qualification testing frequency of peer '%s' when OK should a number of milliseconds at line %d of iax.conf\n", peer->name, v->lineno);
12611 }
12612 } else if (!strcasecmp(v->name, "qualifyfreqnotok")) {
12613 if (sscanf(v->value, "%30d", &peer->pokefreqnotok) != 1) {
12614 ast_log(LOG_WARNING, "Qualification testing frequency of peer '%s' when NOT OK should be a number of milliseconds at line %d of iax.conf\n", peer->name, v->lineno);
12615 }
12616 } else if (!strcasecmp(v->name, "timezone")) {
12617 ast_string_field_set(peer, zonetag, v->value);
12618 } else if (!strcasecmp(v->name, "adsi")) {
12619 peer->adsi = ast_true(v->value);
12620 } else if (!strcasecmp(v->name, "connectedline")) {
12621 if (ast_true(v->value)) {
12622 ast_set_flag64(peer, IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
12623 } else if (!strcasecmp(v->value, "send")) {
12624 ast_clear_flag64(peer, IAX_RECVCONNECTEDLINE);
12625 ast_set_flag64(peer, IAX_SENDCONNECTEDLINE);
12626 } else if (!strcasecmp(v->value, "receive")) {
12627 ast_clear_flag64(peer, IAX_SENDCONNECTEDLINE);
12628 ast_set_flag64(peer, IAX_RECVCONNECTEDLINE);
12629 } else {
12630 ast_clear_flag64(peer, IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
12631 }
12632 } else if (!strcasecmp(v->name, "maxcallnumbers")) {
12633 if (sscanf(v->value, "%10hu", &peer->maxcallno) != 1) {
12634 ast_log(LOG_WARNING, "maxcallnumbers must be set to a valid number. %s is not valid at line %d.\n", v->value, v->lineno);
12635 } else {
12636 peercnt_modify(1, peer->maxcallno, &peer->addr);
12637 }
12638 } else if (!strcasecmp(v->name, "requirecalltoken")) {
12639
12640 if (ast_false(v->value)) {
12641 peer->calltoken_required = CALLTOKEN_NO;
12642 } else if (!strcasecmp(v->value, "auto")) {
12643 peer->calltoken_required = CALLTOKEN_AUTO;
12644 } else if (ast_true(v->value)) {
12645 peer->calltoken_required = CALLTOKEN_YES;
12646 } else {
12647 ast_log(LOG_WARNING, "requirecalltoken must be set to a valid value. at line %d\n", v->lineno);
12648 }
12649 }
12650
12651 v = v->next;
12652 if (!v) {
12653 v = alt;
12654 alt = NULL;
12655 }
12656 }
12657 if (!peer->authmethods)
12658 peer->authmethods = IAX_AUTH_MD5 | IAX_AUTH_PLAINTEXT;
12659 ast_clear_flag64(peer, IAX_DELME);
12660 }
12661
12662 if (oldha)
12663 ast_free_ha(oldha);
12664
12665 if (!ast_strlen_zero(peer->mailbox)) {
12666 char *mailbox, *context;
12667 context = mailbox = ast_strdupa(peer->mailbox);
12668 strsep(&context, "@");
12669 if (ast_strlen_zero(context))
12670 context = "default";
12671 peer->mwi_event_sub = ast_event_subscribe(AST_EVENT_MWI, mwi_event_cb, "IAX MWI subscription", NULL,
12672 AST_EVENT_IE_MAILBOX, AST_EVENT_IE_PLTYPE_STR, mailbox,
12673 AST_EVENT_IE_CONTEXT, AST_EVENT_IE_PLTYPE_STR, context,
12674 AST_EVENT_IE_END);
12675 }
12676
12677 return peer;
12678 }
12679
12680 static void user_destructor(void *obj)
12681 {
12682 struct iax2_user *user = obj;
12683
12684 ast_free_ha(user->ha);
12685 free_context(user->contexts);
12686 if(user->vars) {
12687 ast_variables_destroy(user->vars);
12688 user->vars = NULL;
12689 }
12690 ast_string_field_free_memory(user);
12691 }
12692
12693
12694 static struct iax2_user *build_user(const char *name, struct ast_variable *v, struct ast_variable *alt, int temponly)
12695 {
12696 struct iax2_user *user = NULL;
12697 struct iax2_context *con, *conl = NULL;
12698 struct ast_ha *oldha = NULL;
12699 struct iax2_context *oldcon = NULL;
12700 int format;
12701 int firstpass=1;
12702 int oldcurauthreq = 0;
12703 char *varname = NULL, *varval = NULL;
12704 struct ast_variable *tmpvar = NULL;
12705 struct iax2_user tmp_user = {
12706 .name = name,
12707 };
12708
12709 if (!temponly) {
12710 user = ao2_find(users, &tmp_user, OBJ_POINTER);
12711 if (user && !ast_test_flag64(user, IAX_DELME))
12712 firstpass = 0;
12713 }
12714
12715 if (user) {
12716 if (firstpass) {
12717 oldcurauthreq = user->curauthreq;
12718 oldha = user->ha;
12719 oldcon = user->contexts;
12720 user->ha = NULL;
12721 user->contexts = NULL;
12722 }
12723
12724 ao2_unlink(users, user);
12725 } else {
12726 user = ao2_alloc(sizeof(*user), user_destructor);
12727 }
12728
12729 if (user) {
12730 if (firstpass) {
12731 ast_string_field_free_memory(user);
12732 memset(user, 0, sizeof(struct iax2_user));
12733 if (ast_string_field_init(user, 32)) {
12734 user = user_unref(user);
12735 goto cleanup;
12736 }
12737 user->maxauthreq = maxauthreq;
12738 user->curauthreq = oldcurauthreq;
12739 user->prefs = prefs;
12740 user->capability = iax2_capability;
12741 user->encmethods = iax2_encryption;
12742 user->adsi = adsi;
12743 user->calltoken_required = CALLTOKEN_DEFAULT;
12744 ast_string_field_set(user, name, name);
12745 ast_string_field_set(user, language, language);
12746 ast_copy_flags64(user, &globalflags, IAX_USEJITTERBUF | IAX_FORCEJITTERBUF | IAX_CODEC_USER_FIRST | IAX_CODEC_NOPREFS | IAX_CODEC_NOCAP | IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE | IAX_FORCE_ENCRYPT);
12747 ast_clear_flag64(user, IAX_HASCALLERID);
12748 ast_string_field_set(user, cid_name, "");
12749 ast_string_field_set(user, cid_num, "");
12750 ast_string_field_set(user, accountcode, accountcode);
12751 ast_string_field_set(user, mohinterpret, mohinterpret);
12752 ast_string_field_set(user, mohsuggest, mohsuggest);
12753 }
12754 if (!v) {
12755 v = alt;
12756 alt = NULL;
12757 }
12758 while(v) {
12759 if (!strcasecmp(v->name, "context")) {
12760 con = build_context(v->value);
12761 if (con) {
12762 if (conl)
12763 conl->next = con;
12764 else
12765 user->contexts = con;
12766 conl = con;
12767 }
12768 } else if (!strcasecmp(v->name, "permit") ||
12769 !strcasecmp(v->name, "deny")) {
12770 user->ha = ast_append_ha(v->name, v->value, user->ha, NULL);
12771 } else if (!strcasecmp(v->name, "setvar")) {
12772 varname = ast_strdupa(v->value);
12773 if (varname && (varval = strchr(varname,'='))) {
12774 *varval = '\0';
12775 varval++;
12776 if((tmpvar = ast_variable_new(varname, varval, ""))) {
12777 tmpvar->next = user->vars;
12778 user->vars = tmpvar;
12779 }
12780 }
12781 } else if (!strcasecmp(v->name, "allow")) {
12782 ast_parse_allow_disallow(&user->prefs, &user->capability, v->value, 1);
12783 } else if (!strcasecmp(v->name, "disallow")) {
12784 ast_parse_allow_disallow(&user->prefs, &user->capability,v->value, 0);
12785 } else if (!strcasecmp(v->name, "trunk")) {
12786 ast_set2_flag64(user, ast_true(v->value), IAX_TRUNK);
12787 if (ast_test_flag64(user, IAX_TRUNK) && !timer) {
12788 ast_log(LOG_WARNING, "Unable to support trunking on user '%s' without a timing interface\n", user->name);
12789 ast_clear_flag64(user, IAX_TRUNK);
12790 }
12791 } else if (!strcasecmp(v->name, "auth")) {
12792 user->authmethods = get_auth_methods(v->value);
12793 } else if (!strcasecmp(v->name, "encryption")) {
12794 user->encmethods |= get_encrypt_methods(v->value);
12795 if (!user->encmethods) {
12796 ast_clear_flag64(user, IAX_FORCE_ENCRYPT);
12797 }
12798 } else if (!strcasecmp(v->name, "forceencryption")) {
12799 if (ast_false(v->value)) {
12800 ast_clear_flag64(user, IAX_FORCE_ENCRYPT);
12801 } else {
12802 user->encmethods |= get_encrypt_methods(v->value);
12803 if (user->encmethods) {
12804 ast_set_flag64(user, IAX_FORCE_ENCRYPT);
12805 }
12806 }
12807 } else if (!strcasecmp(v->name, "transfer")) {
12808 if (!strcasecmp(v->value, "mediaonly")) {
12809 ast_set_flags_to64(user, IAX_NOTRANSFER|IAX_TRANSFERMEDIA, IAX_TRANSFERMEDIA);
12810 } else if (ast_true(v->value)) {
12811 ast_set_flags_to64(user, IAX_NOTRANSFER|IAX_TRANSFERMEDIA, 0);
12812 } else
12813 ast_set_flags_to64(user, IAX_NOTRANSFER|IAX_TRANSFERMEDIA, IAX_NOTRANSFER);
12814 } else if (!strcasecmp(v->name, "codecpriority")) {
12815 if(!strcasecmp(v->value, "caller"))
12816 ast_set_flag64(user, IAX_CODEC_USER_FIRST);
12817 else if(!strcasecmp(v->value, "disabled"))
12818 ast_set_flag64(user, IAX_CODEC_NOPREFS);
12819 else if(!strcasecmp(v->value, "reqonly")) {
12820 ast_set_flag64(user, IAX_CODEC_NOCAP);
12821 ast_set_flag64(user, IAX_CODEC_NOPREFS);
12822 }
12823 } else if (!strcasecmp(v->name, "immediate")) {
12824 ast_set2_flag64(user, ast_true(v->value), IAX_IMMEDIATE);
12825 } else if (!strcasecmp(v->name, "jitterbuffer")) {
12826 ast_set2_flag64(user, ast_true(v->value), IAX_USEJITTERBUF);
12827 } else if (!strcasecmp(v->name, "forcejitterbuffer")) {
12828 ast_set2_flag64(user, ast_true(v->value), IAX_FORCEJITTERBUF);
12829 } else if (!strcasecmp(v->name, "dbsecret")) {
12830 ast_string_field_set(user, dbsecret, v->value);
12831 } else if (!strcasecmp(v->name, "secret")) {
12832 if (!ast_strlen_zero(user->secret)) {
12833 char *old = ast_strdupa(user->secret);
12834
12835 ast_string_field_build(user, secret, "%s;%s", old, v->value);
12836 } else
12837 ast_string_field_set(user, secret, v->value);
12838 } else if (!strcasecmp(v->name, "callerid")) {
12839 if (!ast_strlen_zero(v->value) && strcasecmp(v->value, "asreceived")) {
12840 char name2[80];
12841 char num2[80];
12842 ast_callerid_split(v->value, name2, sizeof(name2), num2, sizeof(num2));
12843 ast_string_field_set(user, cid_name, name2);
12844 ast_string_field_set(user, cid_num, num2);
12845 ast_set_flag64(user, IAX_HASCALLERID);
12846 } else {
12847 ast_clear_flag64(user, IAX_HASCALLERID);
12848 ast_string_field_set(user, cid_name, "");
12849 ast_string_field_set(user, cid_num, "");
12850 }
12851 } else if (!strcasecmp(v->name, "fullname")) {
12852 if (!ast_strlen_zero(v->value)) {
12853 ast_string_field_set(user, cid_name, v->value);
12854 ast_set_flag64(user, IAX_HASCALLERID);
12855 } else {
12856 ast_string_field_set(user, cid_name, "");
12857 if (ast_strlen_zero(user->cid_num))
12858 ast_clear_flag64(user, IAX_HASCALLERID);
12859 }
12860 } else if (!strcasecmp(v->name, "cid_number")) {
12861 if (!ast_strlen_zero(v->value)) {
12862 ast_string_field_set(user, cid_num, v->value);
12863 ast_set_flag64(user, IAX_HASCALLERID);
12864 } else {
12865 ast_string_field_set(user, cid_num, "");
12866 if (ast_strlen_zero(user->cid_name))
12867 ast_clear_flag64(user, IAX_HASCALLERID);
12868 }
12869 } else if (!strcasecmp(v->name, "accountcode")) {
12870 ast_string_field_set(user, accountcode, v->value);
12871 } else if (!strcasecmp(v->name, "mohinterpret")) {
12872 ast_string_field_set(user, mohinterpret, v->value);
12873 } else if (!strcasecmp(v->name, "mohsuggest")) {
12874 ast_string_field_set(user, mohsuggest, v->value);
12875 } else if (!strcasecmp(v->name, "parkinglot")) {
12876 ast_string_field_set(user, parkinglot, v->value);
12877 } else if (!strcasecmp(v->name, "language")) {
12878 ast_string_field_set(user, language, v->value);
12879 } else if (!strcasecmp(v->name, "amaflags")) {
12880 format = ast_cdr_amaflags2int(v->value);
12881 if (format < 0) {
12882 ast_log(LOG_WARNING, "Invalid AMA Flags: %s at line %d\n", v->value, v->lineno);
12883 } else {
12884 user->amaflags = format;
12885 }
12886 } else if (!strcasecmp(v->name, "inkeys")) {
12887 ast_string_field_set(user, inkeys, v->value);
12888 } else if (!strcasecmp(v->name, "maxauthreq")) {
12889 user->maxauthreq = atoi(v->value);
12890 if (user->maxauthreq < 0)
12891 user->maxauthreq = 0;
12892 } else if (!strcasecmp(v->name, "adsi")) {
12893 user->adsi = ast_true(v->value);
12894 } else if (!strcasecmp(v->name, "connectedline")) {
12895 if (ast_true(v->value)) {
12896 ast_set_flag64(user, IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
12897 } else if (!strcasecmp(v->value, "send")) {
12898 ast_clear_flag64(user, IAX_RECVCONNECTEDLINE);
12899 ast_set_flag64(user, IAX_SENDCONNECTEDLINE);
12900 } else if (!strcasecmp(v->value, "receive")) {
12901 ast_clear_flag64(user, IAX_SENDCONNECTEDLINE);
12902 ast_set_flag64(user, IAX_RECVCONNECTEDLINE);
12903 } else {
12904 ast_clear_flag64(user, IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
12905 }
12906 } else if (!strcasecmp(v->name, "requirecalltoken")) {
12907
12908 if (ast_false(v->value)) {
12909 user->calltoken_required = CALLTOKEN_NO;
12910 } else if (!strcasecmp(v->value, "auto")) {
12911 user->calltoken_required = CALLTOKEN_AUTO;
12912 } else if (ast_true(v->value)) {
12913 user->calltoken_required = CALLTOKEN_YES;
12914 } else {
12915 ast_log(LOG_WARNING, "requirecalltoken must be set to a valid value. at line %d\n", v->lineno);
12916 }
12917 }
12918
12919 v = v->next;
12920 if (!v) {
12921 v = alt;
12922 alt = NULL;
12923 }
12924 }
12925 if (!user->authmethods) {
12926 if (!ast_strlen_zero(user->secret)) {
12927 user->authmethods = IAX_AUTH_MD5 | IAX_AUTH_PLAINTEXT;
12928 if (!ast_strlen_zero(user->inkeys))
12929 user->authmethods |= IAX_AUTH_RSA;
12930 } else if (!ast_strlen_zero(user->inkeys)) {
12931 user->authmethods = IAX_AUTH_RSA;
12932 } else {
12933 user->authmethods = IAX_AUTH_MD5 | IAX_AUTH_PLAINTEXT;
12934 }
12935 }
12936 ast_clear_flag64(user, IAX_DELME);
12937 }
12938 cleanup:
12939 if (oldha)
12940 ast_free_ha(oldha);
12941 if (oldcon)
12942 free_context(oldcon);
12943 return user;
12944 }
12945
12946 static int peer_delme_cb(void *obj, void *arg, int flags)
12947 {
12948 struct iax2_peer *peer = obj;
12949
12950 ast_set_flag64(peer, IAX_DELME);
12951
12952 return 0;
12953 }
12954
12955 static int user_delme_cb(void *obj, void *arg, int flags)
12956 {
12957 struct iax2_user *user = obj;
12958
12959 ast_set_flag64(user, IAX_DELME);
12960
12961 return 0;
12962 }
12963
12964 static void delete_users(void)
12965 {
12966 struct iax2_registry *reg;
12967
12968 ao2_callback(users, 0, user_delme_cb, NULL);
12969
12970 AST_LIST_LOCK(®istrations);
12971 while ((reg = AST_LIST_REMOVE_HEAD(®istrations, entry))) {
12972 if (sched) {
12973 ast_sched_thread_del(sched, reg->expire);
12974 }
12975 if (reg->callno) {
12976 int callno = reg->callno;
12977 ast_mutex_lock(&iaxsl[callno]);
12978 if (iaxs[callno]) {
12979 iaxs[callno]->reg = NULL;
12980 iax2_destroy(callno);
12981 }
12982 ast_mutex_unlock(&iaxsl[callno]);
12983 }
12984 if (reg->dnsmgr)
12985 ast_dnsmgr_release(reg->dnsmgr);
12986 ast_free(reg);
12987 }
12988 AST_LIST_UNLOCK(®istrations);
12989
12990 ao2_callback(peers, 0, peer_delme_cb, NULL);
12991 }
12992
12993 static void prune_users(void)
12994 {
12995 struct iax2_user *user;
12996 struct ao2_iterator i;
12997
12998 i = ao2_iterator_init(users, 0);
12999 while ((user = ao2_iterator_next(&i))) {
13000 if (ast_test_flag64(user, IAX_DELME) || ast_test_flag64(user, IAX_RTCACHEFRIENDS)) {
13001 ao2_unlink(users, user);
13002 }
13003 user_unref(user);
13004 }
13005 ao2_iterator_destroy(&i);
13006 }
13007
13008
13009 static void prune_peers(void)
13010 {
13011 struct iax2_peer *peer;
13012 struct ao2_iterator i;
13013
13014 i = ao2_iterator_init(peers, 0);
13015 while ((peer = ao2_iterator_next(&i))) {
13016 if (ast_test_flag64(peer, IAX_DELME) || ast_test_flag64(peer, IAX_RTCACHEFRIENDS)) {
13017 unlink_peer(peer);
13018 }
13019 peer_unref(peer);
13020 }
13021 ao2_iterator_destroy(&i);
13022 }
13023
13024 static void set_config_destroy(void)
13025 {
13026 strcpy(accountcode, "");
13027 strcpy(language, "");
13028 strcpy(mohinterpret, "");
13029 strcpy(mohsuggest, "");
13030 trunkmaxsize = MAX_TRUNKDATA;
13031 amaflags = 0;
13032 delayreject = 0;
13033 ast_clear_flag64((&globalflags), IAX_NOTRANSFER | IAX_TRANSFERMEDIA | IAX_USEJITTERBUF |
13034 IAX_FORCEJITTERBUF | IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
13035 delete_users();
13036 ao2_callback(callno_limits, OBJ_NODATA, addr_range_delme_cb, NULL);
13037 ao2_callback(calltoken_ignores, OBJ_NODATA, addr_range_delme_cb, NULL);
13038 }
13039
13040
13041 static int set_config(const char *config_file, int reload)
13042 {
13043 struct ast_config *cfg, *ucfg;
13044 format_t capability = iax2_capability;
13045 struct ast_variable *v;
13046 char *cat;
13047 const char *utype;
13048 const char *tosval;
13049 int format;
13050 int portno = IAX_DEFAULT_PORTNO;
13051 int x;
13052 int mtuv;
13053 int subscribe_network_change = 1;
13054 struct iax2_user *user;
13055 struct iax2_peer *peer;
13056 struct ast_netsock *ns;
13057 struct ast_flags config_flags = { reload ? CONFIG_FLAG_FILEUNCHANGED : 0 };
13058 #if 0
13059 static unsigned short int last_port=0;
13060 #endif
13061
13062 cfg = ast_config_load(config_file, config_flags);
13063
13064 if (!cfg) {
13065 ast_log(LOG_ERROR, "Unable to load config %s\n", config_file);
13066 return -1;
13067 } else if (cfg == CONFIG_STATUS_FILEUNCHANGED) {
13068 ucfg = ast_config_load("users.conf", config_flags);
13069 if (ucfg == CONFIG_STATUS_FILEUNCHANGED)
13070 return 0;
13071
13072 ast_clear_flag(&config_flags, CONFIG_FLAG_FILEUNCHANGED);
13073 if ((cfg = ast_config_load(config_file, config_flags)) == CONFIG_STATUS_FILEINVALID) {
13074 ast_log(LOG_ERROR, "Config file %s is in an invalid format. Aborting.\n", config_file);
13075 ast_config_destroy(ucfg);
13076 return 0;
13077 }
13078 if (!cfg) {
13079
13080 ast_log(LOG_ERROR, "Unable to load config %s again\n", config_file);
13081 return -1;
13082 }
13083 } else if (cfg == CONFIG_STATUS_FILEINVALID) {
13084 ast_log(LOG_ERROR, "Config file %s is in an invalid format. Aborting.\n", config_file);
13085 return 0;
13086 } else {
13087 ast_clear_flag(&config_flags, CONFIG_FLAG_FILEUNCHANGED);
13088 if ((ucfg = ast_config_load("users.conf", config_flags)) == CONFIG_STATUS_FILEINVALID) {
13089 ast_log(LOG_ERROR, "Config file users.conf is in an invalid format. Aborting.\n");
13090 ast_config_destroy(cfg);
13091 return 0;
13092 }
13093 }
13094
13095 if (reload) {
13096 set_config_destroy();
13097 }
13098
13099
13100 memset(&prefs, 0 , sizeof(struct ast_codec_pref));
13101
13102
13103 memset(&globalflags, 0, sizeof(globalflags));
13104 ast_set_flag64(&globalflags, IAX_RTUPDATE);
13105 ast_set_flag64((&globalflags), IAX_SHRINKCALLERID);
13106
13107 #ifdef SO_NO_CHECK
13108 nochecksums = 0;
13109 #endif
13110
13111 default_parkinglot[0] = '\0';
13112
13113 min_reg_expire = IAX_DEFAULT_REG_EXPIRE;
13114 max_reg_expire = IAX_DEFAULT_REG_EXPIRE;
13115 global_max_trunk_mtu = MAX_TRUNK_MTU;
13116 global_maxcallno = DEFAULT_MAXCALLNO_LIMIT;
13117 global_maxcallno_nonval = DEFAULT_MAXCALLNO_LIMIT_NONVAL;
13118
13119 maxauthreq = 3;
13120
13121 srvlookup = 0;
13122
13123 v = ast_variable_browse(cfg, "general");
13124
13125
13126 tosval = ast_variable_retrieve(cfg, "general", "tos");
13127 if (tosval) {
13128 if (ast_str2tos(tosval, &qos.tos))
13129 ast_log(LOG_WARNING, "Invalid tos value, refer to QoS documentation\n");
13130 }
13131
13132 tosval = ast_variable_retrieve(cfg, "general", "cos");
13133 if (tosval) {
13134 if (ast_str2cos(tosval, &qos.cos))
13135 ast_log(LOG_WARNING, "Invalid cos value, refer to QoS documentation\n");
13136 }
13137 while(v) {
13138 if (!strcasecmp(v->name, "bindport")){
13139 if (reload)
13140 ast_log(LOG_NOTICE, "Ignoring bindport on reload\n");
13141 else
13142 portno = atoi(v->value);
13143 } else if (!strcasecmp(v->name, "pingtime"))
13144 ping_time = atoi(v->value);
13145 else if (!strcasecmp(v->name, "iaxthreadcount")) {
13146 if (reload) {
13147 if (atoi(v->value) != iaxthreadcount)
13148 ast_log(LOG_NOTICE, "Ignoring any changes to iaxthreadcount during reload\n");
13149 } else {
13150 iaxthreadcount = atoi(v->value);
13151 if (iaxthreadcount < 1) {
13152 ast_log(LOG_NOTICE, "iaxthreadcount must be at least 1.\n");
13153 iaxthreadcount = 1;
13154 } else if (iaxthreadcount > 256) {
13155 ast_log(LOG_NOTICE, "limiting iaxthreadcount to 256\n");
13156 iaxthreadcount = 256;
13157 }
13158 }
13159 } else if (!strcasecmp(v->name, "iaxmaxthreadcount")) {
13160 if (reload) {
13161 AST_LIST_LOCK(&dynamic_list);
13162 iaxmaxthreadcount = atoi(v->value);
13163 AST_LIST_UNLOCK(&dynamic_list);
13164 } else {
13165 iaxmaxthreadcount = atoi(v->value);
13166 if (iaxmaxthreadcount < 0) {
13167 ast_log(LOG_NOTICE, "iaxmaxthreadcount must be at least 0.\n");
13168 iaxmaxthreadcount = 0;
13169 } else if (iaxmaxthreadcount > 256) {
13170 ast_log(LOG_NOTICE, "Limiting iaxmaxthreadcount to 256\n");
13171 iaxmaxthreadcount = 256;
13172 }
13173 }
13174 } else if (!strcasecmp(v->name, "nochecksums")) {
13175 #ifdef SO_NO_CHECK
13176 if (ast_true(v->value))
13177 nochecksums = 1;
13178 else
13179 nochecksums = 0;
13180 #else
13181 if (ast_true(v->value))
13182 ast_log(LOG_WARNING, "Disabling RTP checksums is not supported on this operating system!\n");
13183 #endif
13184 }
13185 else if (!strcasecmp(v->name, "maxjitterbuffer"))
13186 maxjitterbuffer = atoi(v->value);
13187 else if (!strcasecmp(v->name, "resyncthreshold"))
13188 resyncthreshold = atoi(v->value);
13189 else if (!strcasecmp(v->name, "maxjitterinterps"))
13190 maxjitterinterps = atoi(v->value);
13191 else if (!strcasecmp(v->name, "jittertargetextra"))
13192 jittertargetextra = atoi(v->value);
13193 else if (!strcasecmp(v->name, "lagrqtime"))
13194 lagrq_time = atoi(v->value);
13195 else if (!strcasecmp(v->name, "maxregexpire"))
13196 max_reg_expire = atoi(v->value);
13197 else if (!strcasecmp(v->name, "minregexpire"))
13198 min_reg_expire = atoi(v->value);
13199 else if (!strcasecmp(v->name, "bindaddr")) {
13200 if (reload) {
13201 ast_log(LOG_NOTICE, "Ignoring bindaddr on reload\n");
13202 } else {
13203 if (!(ns = ast_netsock_bind(netsock, io, v->value, portno, qos.tos, qos.cos, socket_read, NULL))) {
13204 ast_log(LOG_WARNING, "Unable apply binding to '%s' at line %d\n", v->value, v->lineno);
13205 } else {
13206 if (strchr(v->value, ':'))
13207 ast_verb(2, "Binding IAX2 to '%s'\n", v->value);
13208 else
13209 ast_verb(2, "Binding IAX2 to '%s:%d'\n", v->value, portno);
13210 if (defaultsockfd < 0)
13211 defaultsockfd = ast_netsock_sockfd(ns);
13212 ast_netsock_unref(ns);
13213 }
13214 }
13215 } else if (!strcasecmp(v->name, "authdebug")) {
13216 authdebug = ast_true(v->value);
13217 } else if (!strcasecmp(v->name, "encryption")) {
13218 iax2_encryption |= get_encrypt_methods(v->value);
13219 if (!iax2_encryption) {
13220 ast_clear_flag64((&globalflags), IAX_FORCE_ENCRYPT);
13221 }
13222 } else if (!strcasecmp(v->name, "forceencryption")) {
13223 if (ast_false(v->value)) {
13224 ast_clear_flag64((&globalflags), IAX_FORCE_ENCRYPT);
13225 } else {
13226 iax2_encryption |= get_encrypt_methods(v->value);
13227 if (iax2_encryption) {
13228 ast_set_flag64((&globalflags), IAX_FORCE_ENCRYPT);
13229 }
13230 }
13231 } else if (!strcasecmp(v->name, "transfer")) {
13232 if (!strcasecmp(v->value, "mediaonly")) {
13233 ast_set_flags_to64((&globalflags), IAX_NOTRANSFER|IAX_TRANSFERMEDIA, IAX_TRANSFERMEDIA);
13234 } else if (ast_true(v->value)) {
13235 ast_set_flags_to64((&globalflags), IAX_NOTRANSFER|IAX_TRANSFERMEDIA, 0);
13236 } else
13237 ast_set_flags_to64((&globalflags), IAX_NOTRANSFER|IAX_TRANSFERMEDIA, IAX_NOTRANSFER);
13238 } else if (!strcasecmp(v->name, "codecpriority")) {
13239 if(!strcasecmp(v->value, "caller"))
13240 ast_set_flag64((&globalflags), IAX_CODEC_USER_FIRST);
13241 else if(!strcasecmp(v->value, "disabled"))
13242 ast_set_flag64((&globalflags), IAX_CODEC_NOPREFS);
13243 else if(!strcasecmp(v->value, "reqonly")) {
13244 ast_set_flag64((&globalflags), IAX_CODEC_NOCAP);
13245 ast_set_flag64((&globalflags), IAX_CODEC_NOPREFS);
13246 }
13247 } else if (!strcasecmp(v->name, "jitterbuffer"))
13248 ast_set2_flag64((&globalflags), ast_true(v->value), IAX_USEJITTERBUF);
13249 else if (!strcasecmp(v->name, "forcejitterbuffer"))
13250 ast_set2_flag64((&globalflags), ast_true(v->value), IAX_FORCEJITTERBUF);
13251 else if (!strcasecmp(v->name, "delayreject"))
13252 delayreject = ast_true(v->value);
13253 else if (!strcasecmp(v->name, "allowfwdownload"))
13254 ast_set2_flag64((&globalflags), ast_true(v->value), IAX_ALLOWFWDOWNLOAD);
13255 else if (!strcasecmp(v->name, "rtcachefriends"))
13256 ast_set2_flag64((&globalflags), ast_true(v->value), IAX_RTCACHEFRIENDS);
13257 else if (!strcasecmp(v->name, "rtignoreregexpire"))
13258 ast_set2_flag64((&globalflags), ast_true(v->value), IAX_RTIGNOREREGEXPIRE);
13259 else if (!strcasecmp(v->name, "rtupdate"))
13260 ast_set2_flag64((&globalflags), ast_true(v->value), IAX_RTUPDATE);
13261 else if (!strcasecmp(v->name, "rtsavesysname"))
13262 ast_set2_flag64((&globalflags), ast_true(v->value), IAX_RTSAVE_SYSNAME);
13263 else if (!strcasecmp(v->name, "trunktimestamps"))
13264 ast_set2_flag64(&globalflags, ast_true(v->value), IAX_TRUNKTIMESTAMPS);
13265 else if (!strcasecmp(v->name, "rtautoclear")) {
13266 int i = atoi(v->value);
13267 if(i > 0)
13268 global_rtautoclear = i;
13269 else
13270 i = 0;
13271 ast_set2_flag64((&globalflags), i || ast_true(v->value), IAX_RTAUTOCLEAR);
13272 } else if (!strcasecmp(v->name, "trunkfreq")) {
13273 trunkfreq = atoi(v->value);
13274 if (trunkfreq < 10) {
13275 ast_log(LOG_NOTICE, "trunkfreq must be between 10ms and 1000ms, using 10ms instead.\n");
13276 trunkfreq = 10;
13277 } else if (trunkfreq > 1000) {
13278 ast_log(LOG_NOTICE, "trunkfreq must be between 10ms and 1000ms, using 1000ms instead.\n");
13279 trunkfreq = 1000;
13280 }
13281 if (timer) {
13282 ast_timer_set_rate(timer, 1000 / trunkfreq);
13283 }
13284 } else if (!strcasecmp(v->name, "trunkmtu")) {
13285 mtuv = atoi(v->value);
13286 if (mtuv == 0 )
13287 global_max_trunk_mtu = 0;
13288 else if (mtuv >= 172 && mtuv < 4000)
13289 global_max_trunk_mtu = mtuv;
13290 else
13291 ast_log(LOG_NOTICE, "trunkmtu value out of bounds (%d) at line %d\n",
13292 mtuv, v->lineno);
13293 } else if (!strcasecmp(v->name, "trunkmaxsize")) {
13294 trunkmaxsize = atoi(v->value);
13295 if (trunkmaxsize == 0)
13296 trunkmaxsize = MAX_TRUNKDATA;
13297 } else if (!strcasecmp(v->name, "autokill")) {
13298 if (sscanf(v->value, "%30d", &x) == 1) {
13299 if (x >= 0)
13300 autokill = x;
13301 else
13302 ast_log(LOG_NOTICE, "Nice try, but autokill has to be >0 or 'yes' or 'no' at line %d\n", v->lineno);
13303 } else if (ast_true(v->value)) {
13304 autokill = DEFAULT_MAXMS;
13305 } else {
13306 autokill = 0;
13307 }
13308 } else if (!strcasecmp(v->name, "bandwidth")) {
13309 if (!strcasecmp(v->value, "low")) {
13310 capability = IAX_CAPABILITY_LOWBANDWIDTH;
13311 } else if (!strcasecmp(v->value, "medium")) {
13312 capability = IAX_CAPABILITY_MEDBANDWIDTH;
13313 } else if (!strcasecmp(v->value, "high")) {
13314 capability = IAX_CAPABILITY_FULLBANDWIDTH;
13315 } else
13316 ast_log(LOG_WARNING, "bandwidth must be either low, medium, or high\n");
13317 } else if (!strcasecmp(v->name, "allow")) {
13318 ast_parse_allow_disallow(&prefs, &capability, v->value, 1);
13319 } else if (!strcasecmp(v->name, "disallow")) {
13320 ast_parse_allow_disallow(&prefs, &capability, v->value, 0);
13321 } else if (!strcasecmp(v->name, "register")) {
13322 iax2_register(v->value, v->lineno);
13323 } else if (!strcasecmp(v->name, "iaxcompat")) {
13324 iaxcompat = ast_true(v->value);
13325 } else if (!strcasecmp(v->name, "regcontext")) {
13326 ast_copy_string(regcontext, v->value, sizeof(regcontext));
13327
13328 ast_context_find_or_create(NULL, NULL, regcontext, "IAX2");
13329 } else if (!strcasecmp(v->name, "tos")) {
13330 if (ast_str2tos(v->value, &qos.tos))
13331 ast_log(LOG_WARNING, "Invalid tos value at line %d, refer to QoS documentation\n", v->lineno);
13332 } else if (!strcasecmp(v->name, "cos")) {
13333 if (ast_str2cos(v->value, &qos.cos))
13334 ast_log(LOG_WARNING, "Invalid cos value at line %d, refer to QoS documentation\n", v->lineno);
13335 } else if (!strcasecmp(v->name, "parkinglot")) {
13336 ast_copy_string(default_parkinglot, v->value, sizeof(default_parkinglot));
13337 } else if (!strcasecmp(v->name, "accountcode")) {
13338 ast_copy_string(accountcode, v->value, sizeof(accountcode));
13339 } else if (!strcasecmp(v->name, "mohinterpret")) {
13340 ast_copy_string(mohinterpret, v->value, sizeof(mohinterpret));
13341 } else if (!strcasecmp(v->name, "mohsuggest")) {
13342 ast_copy_string(mohsuggest, v->value, sizeof(mohsuggest));
13343 } else if (!strcasecmp(v->name, "amaflags")) {
13344 format = ast_cdr_amaflags2int(v->value);
13345 if (format < 0) {
13346 ast_log(LOG_WARNING, "Invalid AMA Flags: %s at line %d\n", v->value, v->lineno);
13347 } else {
13348 amaflags = format;
13349 }
13350 } else if (!strcasecmp(v->name, "language")) {
13351 ast_copy_string(language, v->value, sizeof(language));
13352 } else if (!strcasecmp(v->name, "maxauthreq")) {
13353 maxauthreq = atoi(v->value);
13354 if (maxauthreq < 0)
13355 maxauthreq = 0;
13356 } else if (!strcasecmp(v->name, "adsi")) {
13357 adsi = ast_true(v->value);
13358 } else if (!strcasecmp(v->name, "srvlookup")) {
13359 srvlookup = ast_true(v->value);
13360 } else if (!strcasecmp(v->name, "connectedline")) {
13361 if (ast_true(v->value)) {
13362 ast_set_flag64((&globalflags), IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
13363 } else if (!strcasecmp(v->value, "send")) {
13364 ast_clear_flag64((&globalflags), IAX_RECVCONNECTEDLINE);
13365 ast_set_flag64((&globalflags), IAX_SENDCONNECTEDLINE);
13366 } else if (!strcasecmp(v->value, "receive")) {
13367 ast_clear_flag64((&globalflags), IAX_SENDCONNECTEDLINE);
13368 ast_set_flag64((&globalflags), IAX_RECVCONNECTEDLINE);
13369 } else {
13370 ast_clear_flag64((&globalflags), IAX_SENDCONNECTEDLINE | IAX_RECVCONNECTEDLINE);
13371 }
13372 } else if (!strcasecmp(v->name, "maxcallnumbers")) {
13373 if (sscanf(v->value, "%10hu", &global_maxcallno) != 1) {
13374 ast_log(LOG_WARNING, "maxcallnumbers must be set to a valid number. %s is not valid at line %d\n", v->value, v->lineno);
13375 }
13376 } else if (!strcasecmp(v->name, "maxcallnumbers_nonvalidated")) {
13377 if (sscanf(v->value, "%10hu", &global_maxcallno_nonval) != 1) {
13378 ast_log(LOG_WARNING, "maxcallnumbers_nonvalidated must be set to a valid number. %s is not valid at line %d.\n", v->value, v->lineno);
13379 }
13380 } else if (!strcasecmp(v->name, "calltokenoptional")) {
13381 if (add_calltoken_ignore(v->value)) {
13382 ast_log(LOG_WARNING, "Invalid calltokenoptional address range - '%s' line %d\n", v->value, v->lineno);
13383 }
13384 } else if (!strcasecmp(v->name, "subscribe_network_change_event")) {
13385 if (ast_true(v->value)) {
13386 subscribe_network_change = 1;
13387 } else if (ast_false(v->value)) {
13388 subscribe_network_change = 0;
13389 } else {
13390 ast_log(LOG_WARNING, "subscribe_network_change_event value %s is not valid at line %d.\n", v->value, v->lineno);
13391 }
13392 } else if (!strcasecmp(v->name, "shrinkcallerid")) {
13393 if (ast_true(v->value)) {
13394 ast_set_flag64((&globalflags), IAX_SHRINKCALLERID);
13395 } else if (ast_false(v->value)) {
13396 ast_clear_flag64((&globalflags), IAX_SHRINKCALLERID);
13397 } else {
13398 ast_log(LOG_WARNING, "shrinkcallerid value %s is not valid at line %d.\n", v->value, v->lineno);
13399 }
13400 }
13401
13402 v = v->next;
13403 }
13404
13405 if (subscribe_network_change) {
13406 network_change_event_subscribe();
13407 } else {
13408 network_change_event_unsubscribe();
13409 }
13410
13411 if (defaultsockfd < 0) {
13412 if (!(ns = ast_netsock_bind(netsock, io, "0.0.0.0", portno, qos.tos, qos.cos, socket_read, NULL))) {
13413 ast_log(LOG_ERROR, "Unable to create network socket: %s\n", strerror(errno));
13414 } else {
13415 ast_verb(2, "Binding IAX2 to default address 0.0.0.0:%d\n", portno);
13416 defaultsockfd = ast_netsock_sockfd(ns);
13417 ast_netsock_unref(ns);
13418 }
13419 }
13420 if (reload) {
13421 ast_netsock_release(outsock);
13422 outsock = ast_netsock_list_alloc();
13423 if (!outsock) {
13424 ast_log(LOG_ERROR, "Could not allocate outsock list.\n");
13425 return -1;
13426 }
13427 ast_netsock_init(outsock);
13428 }
13429
13430 if (min_reg_expire > max_reg_expire) {
13431 ast_log(LOG_WARNING, "Minimum registration interval of %d is more than maximum of %d, resetting minimum to %d\n",
13432 min_reg_expire, max_reg_expire, max_reg_expire);
13433 min_reg_expire = max_reg_expire;
13434 }
13435 iax2_capability = capability;
13436
13437 if (ucfg) {
13438 struct ast_variable *gen;
13439 int genhasiax;
13440 int genregisteriax;
13441 const char *hasiax, *registeriax;
13442
13443 genhasiax = ast_true(ast_variable_retrieve(ucfg, "general", "hasiax"));
13444 genregisteriax = ast_true(ast_variable_retrieve(ucfg, "general", "registeriax"));
13445 gen = ast_variable_browse(ucfg, "general");
13446 cat = ast_category_browse(ucfg, NULL);
13447 while (cat) {
13448 if (strcasecmp(cat, "general")) {
13449 hasiax = ast_variable_retrieve(ucfg, cat, "hasiax");
13450 registeriax = ast_variable_retrieve(ucfg, cat, "registeriax");
13451 if (ast_true(hasiax) || (!hasiax && genhasiax)) {
13452
13453 user = build_user(cat, gen, ast_variable_browse(ucfg, cat), 0);
13454 if (user) {
13455 ao2_link(users, user);
13456 user = user_unref(user);
13457 }
13458 peer = build_peer(cat, gen, ast_variable_browse(ucfg, cat), 0);
13459 if (peer) {
13460 if (ast_test_flag64(peer, IAX_DYNAMIC))
13461 reg_source_db(peer);
13462 ao2_link(peers, peer);
13463 peer = peer_unref(peer);
13464 }
13465 }
13466 if (ast_true(registeriax) || (!registeriax && genregisteriax)) {
13467 char tmp[256];
13468 const char *host = ast_variable_retrieve(ucfg, cat, "host");
13469 const char *username = ast_variable_retrieve(ucfg, cat, "username");
13470 const char *secret = ast_variable_retrieve(ucfg, cat, "secret");
13471 if (!host)
13472 host = ast_variable_retrieve(ucfg, "general", "host");
13473 if (!username)
13474 username = ast_variable_retrieve(ucfg, "general", "username");
13475 if (!secret)
13476 secret = ast_variable_retrieve(ucfg, "general", "secret");
13477 if (!ast_strlen_zero(username) && !ast_strlen_zero(host)) {
13478 if (!ast_strlen_zero(secret))
13479 snprintf(tmp, sizeof(tmp), "%s:%s@%s", username, secret, host);
13480 else
13481 snprintf(tmp, sizeof(tmp), "%s@%s", username, host);
13482 iax2_register(tmp, 0);
13483 }
13484 }
13485 }
13486 cat = ast_category_browse(ucfg, cat);
13487 }
13488 ast_config_destroy(ucfg);
13489 }
13490
13491 cat = ast_category_browse(cfg, NULL);
13492 while(cat) {
13493 if (strcasecmp(cat, "general")) {
13494 utype = ast_variable_retrieve(cfg, cat, "type");
13495 if (!strcasecmp(cat, "callnumberlimits")) {
13496 build_callno_limits(ast_variable_browse(cfg, cat));
13497 } else if (utype) {
13498 if (!strcasecmp(utype, "user") || !strcasecmp(utype, "friend")) {
13499 user = build_user(cat, ast_variable_browse(cfg, cat), NULL, 0);
13500 if (user) {
13501 ao2_link(users, user);
13502 user = user_unref(user);
13503 }
13504 }
13505 if (!strcasecmp(utype, "peer") || !strcasecmp(utype, "friend")) {
13506 peer = build_peer(cat, ast_variable_browse(cfg, cat), NULL, 0);
13507 if (peer) {
13508 if (ast_test_flag64(peer, IAX_DYNAMIC))
13509 reg_source_db(peer);
13510 ao2_link(peers, peer);
13511 peer = peer_unref(peer);
13512 }
13513 } else if (strcasecmp(utype, "user")) {
13514 ast_log(LOG_WARNING, "Unknown type '%s' for '%s' in %s\n", utype, cat, config_file);
13515 }
13516 } else
13517 ast_log(LOG_WARNING, "Section '%s' lacks type\n", cat);
13518 }
13519 cat = ast_category_browse(cfg, cat);
13520 }
13521 ast_config_destroy(cfg);
13522 return 1;
13523 }
13524
13525 static void poke_all_peers(void)
13526 {
13527 struct ao2_iterator i;
13528 struct iax2_peer *peer;
13529
13530 i = ao2_iterator_init(peers, 0);
13531 while ((peer = ao2_iterator_next(&i))) {
13532 iax2_poke_peer(peer, 0);
13533 peer_unref(peer);
13534 }
13535 ao2_iterator_destroy(&i);
13536 }
13537 static int reload_config(void)
13538 {
13539 static const char config[] = "iax.conf";
13540 struct iax2_registry *reg;
13541
13542 if (set_config(config, 1) > 0) {
13543 prune_peers();
13544 prune_users();
13545 ao2_callback(callno_limits, OBJ_NODATA | OBJ_UNLINK | OBJ_MULTIPLE, prune_addr_range_cb, NULL);
13546 ao2_callback(calltoken_ignores, OBJ_NODATA | OBJ_UNLINK | OBJ_MULTIPLE, prune_addr_range_cb, NULL);
13547 ao2_callback(peercnts, OBJ_NODATA, set_peercnt_limit_all_cb, NULL);
13548 trunk_timed = trunk_untimed = 0;
13549 trunk_nmaxmtu = trunk_maxmtu = 0;
13550 memset(&debugaddr, '\0', sizeof(debugaddr));
13551
13552 AST_LIST_LOCK(®istrations);
13553 AST_LIST_TRAVERSE(®istrations, reg, entry)
13554 iax2_do_register(reg);
13555 AST_LIST_UNLOCK(®istrations);
13556
13557
13558 poke_all_peers();
13559 }
13560
13561 reload_firmware(0);
13562 iax_provision_reload(1);
13563 ast_unload_realtime("iaxpeers");
13564
13565 return 0;
13566 }
13567
13568 static char *handle_cli_iax2_reload(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
13569 {
13570 switch (cmd) {
13571 case CLI_INIT:
13572 e->command = "iax2 reload";
13573 e->usage =
13574 "Usage: iax2 reload\n"
13575 " Reloads IAX configuration from iax.conf\n";
13576 return NULL;
13577 case CLI_GENERATE:
13578 return NULL;
13579 }
13580
13581 reload_config();
13582
13583 return CLI_SUCCESS;
13584 }
13585
13586 static int reload(void)
13587 {
13588 return reload_config();
13589 }
13590
13591 static int cache_get_callno_locked(const char *data)
13592 {
13593 struct sockaddr_in sin;
13594 int x;
13595 int callno;
13596 struct iax_ie_data ied;
13597 struct create_addr_info cai;
13598 struct parsed_dial_string pds;
13599 char *tmpstr;
13600
13601 for (x = 0; x < ARRAY_LEN(iaxs); x++) {
13602
13603
13604 if (!ast_mutex_trylock(&iaxsl[x])) {
13605 if (iaxs[x] && !strcasecmp(data, iaxs[x]->dproot))
13606 return x;
13607 ast_mutex_unlock(&iaxsl[x]);
13608 }
13609 }
13610
13611
13612
13613 memset(&cai, 0, sizeof(cai));
13614 memset(&ied, 0, sizeof(ied));
13615 memset(&pds, 0, sizeof(pds));
13616
13617 tmpstr = ast_strdupa(data);
13618 parse_dial_string(tmpstr, &pds);
13619
13620 if (ast_strlen_zero(pds.peer)) {
13621 ast_log(LOG_WARNING, "No peer provided in the IAX2 dial string '%s'\n", data);
13622 return -1;
13623 }
13624
13625
13626 if (create_addr(pds.peer, NULL, &sin, &cai))
13627 return -1;
13628
13629 ast_debug(1, "peer: %s, username: %s, password: %s, context: %s\n",
13630 pds.peer, pds.username, pds.password, pds.context);
13631
13632 callno = find_callno_locked(0, 0, &sin, NEW_FORCE, cai.sockfd, 0);
13633 if (callno < 1) {
13634 ast_log(LOG_WARNING, "Unable to create call\n");
13635 return -1;
13636 }
13637
13638 ast_string_field_set(iaxs[callno], dproot, data);
13639 iaxs[callno]->capability = IAX_CAPABILITY_FULLBANDWIDTH;
13640
13641 iax_ie_append_short(&ied, IAX_IE_VERSION, IAX_PROTO_VERSION);
13642 iax_ie_append_str(&ied, IAX_IE_CALLED_NUMBER, "TBD");
13643
13644
13645
13646 if (pds.exten)
13647 iax_ie_append_str(&ied, IAX_IE_CALLED_CONTEXT, pds.exten);
13648 if (pds.username)
13649 iax_ie_append_str(&ied, IAX_IE_USERNAME, pds.username);
13650 iax_ie_append_int(&ied, IAX_IE_FORMAT, IAX_CAPABILITY_FULLBANDWIDTH);
13651 iax_ie_append_int(&ied, IAX_IE_CAPABILITY, IAX_CAPABILITY_FULLBANDWIDTH);
13652
13653 if (pds.password)
13654 ast_string_field_set(iaxs[callno], secret, pds.password);
13655 if (pds.key)
13656 ast_string_field_set(iaxs[callno], outkey, pds.key);
13657
13658 add_empty_calltoken_ie(iaxs[callno], &ied);
13659 send_command(iaxs[callno], AST_FRAME_IAX, IAX_COMMAND_NEW, 0, ied.buf, ied.pos, -1);
13660
13661 return callno;
13662 }
13663
13664 static struct iax2_dpcache *find_cache(struct ast_channel *chan, const char *data, const char *context, const char *exten, int priority)
13665 {
13666 struct iax2_dpcache *dp = NULL;
13667 struct timeval now = ast_tvnow();
13668 int x, com[2], timeout, old = 0, outfd, doabort, callno;
13669 struct ast_channel *c = NULL;
13670 struct ast_frame *f = NULL;
13671
13672 AST_LIST_TRAVERSE_SAFE_BEGIN(&dpcache, dp, cache_list) {
13673 if (ast_tvcmp(now, dp->expiry) > 0) {
13674 AST_LIST_REMOVE_CURRENT(cache_list);
13675 if ((dp->flags & CACHE_FLAG_PENDING) || dp->callno)
13676 ast_log(LOG_WARNING, "DP still has peer field or pending or callno (flags = %d, peer = blah, callno = %d)\n", dp->flags, dp->callno);
13677 else
13678 ast_free(dp);
13679 continue;
13680 }
13681 if (!strcmp(dp->peercontext, data) && !strcmp(dp->exten, exten))
13682 break;
13683 }
13684 AST_LIST_TRAVERSE_SAFE_END;
13685
13686 if (!dp) {
13687
13688
13689 if ((callno = cache_get_callno_locked(data)) < 0) {
13690 ast_log(LOG_WARNING, "Unable to generate call for '%s'\n", data);
13691 return NULL;
13692 }
13693 if (!(dp = ast_calloc(1, sizeof(*dp)))) {
13694 ast_mutex_unlock(&iaxsl[callno]);
13695 return NULL;
13696 }
13697 ast_copy_string(dp->peercontext, data, sizeof(dp->peercontext));
13698 ast_copy_string(dp->exten, exten, sizeof(dp->exten));
13699 dp->expiry = ast_tvnow();
13700 dp->orig = dp->expiry;
13701
13702 dp->expiry.tv_sec += iaxdefaultdpcache;
13703 dp->flags = CACHE_FLAG_PENDING;
13704 for (x = 0; x < ARRAY_LEN(dp->waiters); x++)
13705 dp->waiters[x] = -1;
13706
13707 AST_LIST_INSERT_TAIL(&dpcache, dp, cache_list);
13708 AST_LIST_INSERT_TAIL(&iaxs[callno]->dpentries, dp, peer_list);
13709
13710 if (ast_test_flag(&iaxs[callno]->state, IAX_STATE_STARTED))
13711 iax2_dprequest(dp, callno);
13712 ast_mutex_unlock(&iaxsl[callno]);
13713 }
13714
13715
13716 if (dp->flags & CACHE_FLAG_PENDING) {
13717
13718
13719 for (x = 0; x < ARRAY_LEN(dp->waiters); x++) {
13720
13721 if (dp->waiters[x] < 0)
13722 break;
13723 }
13724 if (x >= ARRAY_LEN(dp->waiters)) {
13725 ast_log(LOG_WARNING, "No more waiter positions available\n");
13726 return NULL;
13727 }
13728 if (pipe(com)) {
13729 ast_log(LOG_WARNING, "Unable to create pipe for comm\n");
13730 return NULL;
13731 }
13732 dp->waiters[x] = com[1];
13733
13734 timeout = iaxdefaulttimeout * 1000;
13735
13736 AST_LIST_UNLOCK(&dpcache);
13737
13738 if (chan)
13739 old = ast_channel_defer_dtmf(chan);
13740 doabort = 0;
13741 while(timeout) {
13742 c = ast_waitfor_nandfds(&chan, chan ? 1 : 0, &com[0], 1, NULL, &outfd, &timeout);
13743 if (outfd > -1)
13744 break;
13745 if (!c)
13746 continue;
13747 if (!(f = ast_read(c))) {
13748 doabort = 1;
13749 break;
13750 }
13751 ast_frfree(f);
13752 }
13753 if (!timeout) {
13754 ast_log(LOG_WARNING, "Timeout waiting for %s exten %s\n", data, exten);
13755 }
13756 AST_LIST_LOCK(&dpcache);
13757 dp->waiters[x] = -1;
13758 close(com[1]);
13759 close(com[0]);
13760 if (doabort) {
13761
13762
13763 if (!old && chan)
13764 ast_channel_undefer_dtmf(chan);
13765 return NULL;
13766 }
13767 if (!(dp->flags & CACHE_FLAG_TIMEOUT)) {
13768
13769 if (dp->flags & CACHE_FLAG_PENDING) {
13770
13771
13772 dp->flags &= ~CACHE_FLAG_PENDING;
13773 dp->flags |= CACHE_FLAG_TIMEOUT;
13774
13775
13776 dp->expiry.tv_sec = dp->orig.tv_sec + 60;
13777 for (x = 0; x < ARRAY_LEN(dp->waiters); x++) {
13778 if (dp->waiters[x] > -1) {
13779 if (write(dp->waiters[x], "asdf", 4) < 0) {
13780 ast_log(LOG_WARNING, "write() failed: %s\n", strerror(errno));
13781 }
13782 }
13783 }
13784 }
13785 }
13786
13787 if (!old && chan)
13788 ast_channel_undefer_dtmf(chan);
13789 }
13790 return dp;
13791 }
13792
13793
13794 static int iax2_exists(struct ast_channel *chan, const char *context, const char *exten, int priority, const char *callerid, const char *data)
13795 {
13796 int res = 0;
13797 struct iax2_dpcache *dp = NULL;
13798 #if 0
13799 ast_log(LOG_NOTICE, "iax2_exists: con: %s, exten: %s, pri: %d, cid: %s, data: %s\n", context, exten, priority, callerid ? callerid : "<unknown>", data);
13800 #endif
13801 if ((priority != 1) && (priority != 2))
13802 return 0;
13803
13804 AST_LIST_LOCK(&dpcache);
13805 if ((dp = find_cache(chan, data, context, exten, priority))) {
13806 if (dp->flags & CACHE_FLAG_EXISTS)
13807 res = 1;
13808 } else {
13809 ast_log(LOG_WARNING, "Unable to make DP cache\n");
13810 }
13811 AST_LIST_UNLOCK(&dpcache);
13812
13813 return res;
13814 }
13815
13816
13817 static int iax2_canmatch(struct ast_channel *chan, const char *context, const char *exten, int priority, const char *callerid, const char *data)
13818 {
13819 int res = 0;
13820 struct iax2_dpcache *dp = NULL;
13821 #if 0
13822 ast_log(LOG_NOTICE, "iax2_canmatch: con: %s, exten: %s, pri: %d, cid: %s, data: %s\n", context, exten, priority, callerid ? callerid : "<unknown>", data);
13823 #endif
13824 if ((priority != 1) && (priority != 2))
13825 return 0;
13826
13827 AST_LIST_LOCK(&dpcache);
13828 if ((dp = find_cache(chan, data, context, exten, priority))) {
13829 if (dp->flags & CACHE_FLAG_CANEXIST)
13830 res = 1;
13831 } else {
13832 ast_log(LOG_WARNING, "Unable to make DP cache\n");
13833 }
13834 AST_LIST_UNLOCK(&dpcache);
13835
13836 return res;
13837 }
13838
13839
13840 static int iax2_matchmore(struct ast_channel *chan, const char *context, const char *exten, int priority, const char *callerid, const char *data)
13841 {
13842 int res = 0;
13843 struct iax2_dpcache *dp = NULL;
13844 #if 0
13845 ast_log(LOG_NOTICE, "iax2_matchmore: con: %s, exten: %s, pri: %d, cid: %s, data: %s\n", context, exten, priority, callerid ? callerid : "<unknown>", data);
13846 #endif
13847 if ((priority != 1) && (priority != 2))
13848 return 0;
13849
13850 AST_LIST_LOCK(&dpcache);
13851 if ((dp = find_cache(chan, data, context, exten, priority))) {
13852 if (dp->flags & CACHE_FLAG_MATCHMORE)
13853 res = 1;
13854 } else {
13855 ast_log(LOG_WARNING, "Unable to make DP cache\n");
13856 }
13857 AST_LIST_UNLOCK(&dpcache);
13858
13859 return res;
13860 }
13861
13862
13863 static int iax2_exec(struct ast_channel *chan, const char *context, const char *exten, int priority, const char *callerid, const char *data)
13864 {
13865 char odata[256];
13866 char req[256];
13867 char *ncontext;
13868 struct iax2_dpcache *dp = NULL;
13869 struct ast_app *dial = NULL;
13870 #if 0
13871 ast_log(LOG_NOTICE, "iax2_exec: con: %s, exten: %s, pri: %d, cid: %s, data: %s, newstack: %d\n", context, exten, priority, callerid ? callerid : "<unknown>", data, newstack);
13872 #endif
13873 if (priority == 2) {
13874
13875 const char *dialstatus = pbx_builtin_getvar_helper(chan, "DIALSTATUS");
13876 if (dialstatus) {
13877 dial = pbx_findapp(dialstatus);
13878 if (dial)
13879 pbx_exec(chan, dial, "");
13880 }
13881 return -1;
13882 } else if (priority != 1)
13883 return -1;
13884
13885 AST_LIST_LOCK(&dpcache);
13886 if ((dp = find_cache(chan, data, context, exten, priority))) {
13887 if (dp->flags & CACHE_FLAG_EXISTS) {
13888 ast_copy_string(odata, data, sizeof(odata));
13889 ncontext = strchr(odata, '/');
13890 if (ncontext) {
13891 *ncontext = '\0';
13892 ncontext++;
13893 snprintf(req, sizeof(req), "IAX2/%s/%s@%s", odata, exten, ncontext);
13894 } else {
13895 snprintf(req, sizeof(req), "IAX2/%s/%s", odata, exten);
13896 }
13897 ast_verb(3, "Executing Dial('%s')\n", req);
13898 } else {
13899 AST_LIST_UNLOCK(&dpcache);
13900 ast_log(LOG_WARNING, "Can't execute nonexistent extension '%s[@%s]' in data '%s'\n", exten, context, data);
13901 return -1;
13902 }
13903 }
13904 AST_LIST_UNLOCK(&dpcache);
13905
13906 if ((dial = pbx_findapp("Dial")))
13907 return pbx_exec(chan, dial, req);
13908 else
13909 ast_log(LOG_WARNING, "No dial application registered\n");
13910
13911 return -1;
13912 }
13913
13914 static int function_iaxpeer(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)
13915 {
13916 struct iax2_peer *peer;
13917 char *peername, *colname;
13918
13919 peername = ast_strdupa(data);
13920
13921
13922 if (!strcmp(peername,"CURRENTCHANNEL")) {
13923 unsigned short callno;
13924 if (chan->tech != &iax2_tech)
13925 return -1;
13926 callno = PTR_TO_CALLNO(chan->tech_pvt);
13927 ast_copy_string(buf, iaxs[callno]->addr.sin_addr.s_addr ? ast_inet_ntoa(iaxs[callno]->addr.sin_addr) : "", len);
13928 return 0;
13929 }
13930
13931 if ((colname = strchr(peername, ',')))
13932 *colname++ = '\0';
13933 else
13934 colname = "ip";
13935
13936 if (!(peer = find_peer(peername, 1)))
13937 return -1;
13938
13939 if (!strcasecmp(colname, "ip")) {
13940 ast_copy_string(buf, ast_sockaddr_stringify_addr(&peer->addr), len);
13941 } else if (!strcasecmp(colname, "status")) {
13942 peer_status(peer, buf, len);
13943 } else if (!strcasecmp(colname, "mailbox")) {
13944 ast_copy_string(buf, peer->mailbox, len);
13945 } else if (!strcasecmp(colname, "context")) {
13946 ast_copy_string(buf, peer->context, len);
13947 } else if (!strcasecmp(colname, "expire")) {
13948 snprintf(buf, len, "%d", peer->expire);
13949 } else if (!strcasecmp(colname, "dynamic")) {
13950 ast_copy_string(buf, (ast_test_flag64(peer, IAX_DYNAMIC) ? "yes" : "no"), len);
13951 } else if (!strcasecmp(colname, "callerid_name")) {
13952 ast_copy_string(buf, peer->cid_name, len);
13953 } else if (!strcasecmp(colname, "callerid_num")) {
13954 ast_copy_string(buf, peer->cid_num, len);
13955 } else if (!strcasecmp(colname, "codecs")) {
13956 ast_getformatname_multiple(buf, len -1, peer->capability);
13957 } else if (!strncasecmp(colname, "codec[", 6)) {
13958 char *codecnum, *ptr;
13959 int codec = 0;
13960
13961
13962 codecnum = colname + 5;
13963 *codecnum = '\0';
13964 codecnum++;
13965 if ((ptr = strchr(codecnum, ']'))) {
13966 *ptr = '\0';
13967 }
13968 if((codec = ast_codec_pref_index(&peer->prefs, atoi(codecnum)))) {
13969 ast_copy_string(buf, ast_getformatname(codec), len);
13970 } else {
13971 buf[0] = '\0';
13972 }
13973 } else {
13974 buf[0] = '\0';
13975 }
13976
13977 peer_unref(peer);
13978
13979 return 0;
13980 }
13981
13982 static struct ast_custom_function iaxpeer_function = {
13983 .name = "IAXPEER",
13984 .read = function_iaxpeer,
13985 };
13986
13987 static int acf_channel_read(struct ast_channel *chan, const char *funcname, char *args, char *buf, size_t buflen)
13988 {
13989 struct chan_iax2_pvt *pvt;
13990 unsigned int callno;
13991 int res = 0;
13992
13993 if (!chan || chan->tech != &iax2_tech) {
13994 ast_log(LOG_ERROR, "This function requires a valid IAX2 channel\n");
13995 return -1;
13996 }
13997
13998 callno = PTR_TO_CALLNO(chan->tech_pvt);
13999 ast_mutex_lock(&iaxsl[callno]);
14000 if (!(pvt = iaxs[callno])) {
14001 ast_mutex_unlock(&iaxsl[callno]);
14002 return -1;
14003 }
14004
14005 if (!strcasecmp(args, "osptoken")) {
14006 ast_copy_string(buf, pvt->osptoken, buflen);
14007 } else if (!strcasecmp(args, "peerip")) {
14008 ast_copy_string(buf, pvt->addr.sin_addr.s_addr ? ast_inet_ntoa(pvt->addr.sin_addr) : "", buflen);
14009 } else if (!strcasecmp(args, "peername")) {
14010 ast_copy_string(buf, pvt->username, buflen);
14011 } else if (!strcasecmp(args, "secure_signaling") || !strcasecmp(args, "secure_media")) {
14012 snprintf(buf, buflen, "%s", IAX_CALLENCRYPTED(pvt) ? "1" : "");
14013 } else {
14014 res = -1;
14015 }
14016
14017 ast_mutex_unlock(&iaxsl[callno]);
14018
14019 return res;
14020 }
14021
14022
14023 static int iax2_devicestate(void *data)
14024 {
14025 struct parsed_dial_string pds;
14026 char *tmp = ast_strdupa(data);
14027 struct iax2_peer *p;
14028 int res = AST_DEVICE_INVALID;
14029
14030 memset(&pds, 0, sizeof(pds));
14031 parse_dial_string(tmp, &pds);
14032
14033 if (ast_strlen_zero(pds.peer)) {
14034 ast_log(LOG_WARNING, "No peer provided in the IAX2 dial string '%s'\n", (char *) data);
14035 return res;
14036 }
14037
14038 ast_debug(3, "Checking device state for device %s\n", pds.peer);
14039
14040
14041 if (!(p = find_peer(pds.peer, 1)))
14042 return res;
14043
14044 res = AST_DEVICE_UNAVAILABLE;
14045 ast_debug(3, "iax2_devicestate: Found peer. What's device state of %s? addr=%d, defaddr=%d maxms=%d, lastms=%d\n",
14046 pds.peer, ast_sockaddr_ipv4(&p->addr), p->defaddr.sin_addr.s_addr, p->maxms, p->lastms);
14047
14048 if ((ast_sockaddr_ipv4(&p->addr) || p->defaddr.sin_addr.s_addr) &&
14049 (!p->maxms || ((p->lastms > -1) && (p->historicms <= p->maxms)))) {
14050
14051
14052 if (p->historicms == 0 || p->historicms <= p->maxms)
14053
14054 res = AST_DEVICE_UNKNOWN;
14055 }
14056
14057 peer_unref(p);
14058
14059 return res;
14060 }
14061
14062 static struct ast_switch iax2_switch =
14063 {
14064 .name = "IAX2",
14065 .description = "IAX Remote Dialplan Switch",
14066 .exists = iax2_exists,
14067 .canmatch = iax2_canmatch,
14068 .exec = iax2_exec,
14069 .matchmore = iax2_matchmore,
14070 };
14071
14072
14073
14074
14075
14076
14077
14078
14079
14080
14081
14082
14083
14084
14085
14086
14087
14088
14089
14090
14091
14092
14093
14094
14095
14096
14097
14098
14099
14100
14101
14102
14103
14104
14105
14106
14107
14108
14109
14110
14111
14112
14113
14114
14115
14116
14117
14118
14119
14120
14121
14122
14123
14124
14125
14126
14127
14128
14129
14130
14131
14132
14133
14134
14135
14136
14137
14138
14139
14140
14141
14142
14143
14144
14145
14146
14147
14148
14149
14150
14151
14152
14153
14154
14155
14156
14157
14158
14159
14160
14161
14162
14163
14164
14165
14166
14167
14168
14169
14170
14171
14172
14173
14174
14175
14176 static struct ast_cli_entry cli_iax2[] = {
14177 AST_CLI_DEFINE(handle_cli_iax2_provision, "Provision an IAX device"),
14178 AST_CLI_DEFINE(handle_cli_iax2_prune_realtime, "Prune a cached realtime lookup"),
14179 AST_CLI_DEFINE(handle_cli_iax2_reload, "Reload IAX configuration"),
14180 AST_CLI_DEFINE(handle_cli_iax2_set_mtu, "Set the IAX systemwide trunking MTU"),
14181 AST_CLI_DEFINE(handle_cli_iax2_set_debug, "Enable/Disable IAX debugging"),
14182 AST_CLI_DEFINE(handle_cli_iax2_set_debug_trunk, "Enable/Disable IAX trunk debugging"),
14183 AST_CLI_DEFINE(handle_cli_iax2_set_debug_jb, "Enable/Disable IAX jitterbuffer debugging"),
14184 AST_CLI_DEFINE(handle_cli_iax2_show_cache, "Display IAX cached dialplan"),
14185 AST_CLI_DEFINE(handle_cli_iax2_show_channels, "List active IAX channels"),
14186 AST_CLI_DEFINE(handle_cli_iax2_show_firmware, "List available IAX firmware"),
14187 AST_CLI_DEFINE(handle_cli_iax2_show_netstats, "List active IAX channel netstats"),
14188 AST_CLI_DEFINE(handle_cli_iax2_show_peer, "Show details on specific IAX peer"),
14189 AST_CLI_DEFINE(handle_cli_iax2_show_peers, "List defined IAX peers"),
14190 AST_CLI_DEFINE(handle_cli_iax2_show_registry, "Display IAX registration status"),
14191 AST_CLI_DEFINE(handle_cli_iax2_show_stats, "Display IAX statistics"),
14192 AST_CLI_DEFINE(handle_cli_iax2_show_threads, "Display IAX helper thread info"),
14193 AST_CLI_DEFINE(handle_cli_iax2_show_users, "List defined IAX users"),
14194 AST_CLI_DEFINE(handle_cli_iax2_test_losspct, "Set IAX2 incoming frame loss percentage"),
14195 AST_CLI_DEFINE(handle_cli_iax2_unregister, "Unregister (force expiration) an IAX2 peer from the registry"),
14196 AST_CLI_DEFINE(handle_cli_iax2_show_callno_limits, "Show current entries in IP call number limit table"),
14197 #ifdef IAXTESTS
14198 AST_CLI_DEFINE(handle_cli_iax2_test_jitter, "Simulates jitter for testing"),
14199 AST_CLI_DEFINE(handle_cli_iax2_test_late, "Test the receipt of a late frame"),
14200 AST_CLI_DEFINE(handle_cli_iax2_test_resync, "Test a resync in received timestamps"),
14201 #endif
14202 };
14203
14204 #ifdef TEST_FRAMEWORK
14205 AST_TEST_DEFINE(test_iax2_peers_get)
14206 {
14207 struct ast_data_query query = {
14208 .path = "/asterisk/channel/iax2/peers",
14209 .search = "peers/peer/name=test_peer_data_provider"
14210 };
14211 struct ast_data *node;
14212 struct iax2_peer *peer;
14213
14214 switch (cmd) {
14215 case TEST_INIT:
14216 info->name = "iax2_peers_get_data_test";
14217 info->category = "/main/data/iax2/peers/";
14218 info->summary = "IAX2 peers data providers unit test";
14219 info->description =
14220 "Tests whether the IAX2 peers data provider implementation works as expected.";
14221 return AST_TEST_NOT_RUN;
14222 case TEST_EXECUTE:
14223 break;
14224 }
14225
14226
14227 peer = build_peer("test_peer_data_provider", NULL, NULL, 0);
14228 if (!peer) {
14229 return AST_TEST_FAIL;
14230 }
14231 peer->expiry= 1010;
14232 ao2_link(peers, peer);
14233
14234 node = ast_data_get(&query);
14235 if (!node) {
14236 ao2_unlink(peers, peer);
14237 peer_unref(peer);
14238 return AST_TEST_FAIL;
14239 }
14240
14241
14242 if (strcmp(ast_data_retrieve_string(node, "peer/name"), "test_peer_data_provider")) {
14243 ao2_unlink(peers, peer);
14244 peer_unref(peer);
14245 ast_data_free(node);
14246 return AST_TEST_FAIL;
14247 }
14248
14249 if (ast_data_retrieve_int(node, "peer/expiry") != 1010) {
14250 ao2_unlink(peers, peer);
14251 peer_unref(peer);
14252 ast_data_free(node);
14253 return AST_TEST_FAIL;
14254 }
14255
14256
14257 ast_data_free(node);
14258
14259 ao2_unlink(peers, peer);
14260 peer_unref(peer);
14261
14262 return AST_TEST_PASS;
14263 }
14264
14265 AST_TEST_DEFINE(test_iax2_users_get)
14266 {
14267 struct ast_data_query query = {
14268 .path = "/asterisk/channel/iax2/users",
14269 .search = "users/user/name=test_user_data_provider"
14270 };
14271 struct ast_data *node;
14272 struct iax2_user *user;
14273
14274 switch (cmd) {
14275 case TEST_INIT:
14276 info->name = "iax2_users_get_data_test";
14277 info->category = "/main/data/iax2/users/";
14278 info->summary = "IAX2 users data providers unit test";
14279 info->description =
14280 "Tests whether the IAX2 users data provider implementation works as expected.";
14281 return AST_TEST_NOT_RUN;
14282 case TEST_EXECUTE:
14283 break;
14284 }
14285
14286 user = build_user("test_user_data_provider", NULL, NULL, 0);
14287 if (!user) {
14288 ast_test_status_update(test, "Failed to build a test user\n");
14289 return AST_TEST_FAIL;
14290 }
14291 user->amaflags = 1010;
14292 ao2_link(users, user);
14293
14294 node = ast_data_get(&query);
14295 if (!node) {
14296 ast_test_status_update(test, "The data query to find our test user failed\n");
14297 ao2_unlink(users, user);
14298 user_unref(user);
14299 return AST_TEST_FAIL;
14300 }
14301
14302 if (strcmp(ast_data_retrieve_string(node, "user/name"), "test_user_data_provider")) {
14303 ast_test_status_update(test, "Our data results did not return the test user created in the previous step.\n");
14304 ao2_unlink(users, user);
14305 user_unref(user);
14306 ast_data_free(node);
14307 return AST_TEST_FAIL;
14308 }
14309
14310 if (ast_data_retrieve_int(node, "user/amaflags/value") != 1010) {
14311 ast_test_status_update(test, "The amaflags field in our test user was '%d' not the expected value '1010'\n", ast_data_retrieve_int(node, "user/amaflags/value"));
14312 ao2_unlink(users, user);
14313 user_unref(user);
14314 ast_data_free(node);
14315 return AST_TEST_FAIL;
14316 }
14317
14318 ast_data_free(node);
14319
14320 ao2_unlink(users, user);
14321 user_unref(user);
14322
14323 return AST_TEST_PASS;
14324 }
14325 #endif
14326
14327 static void cleanup_thread_list(void *head)
14328 {
14329 AST_LIST_HEAD(iax2_thread_list, iax2_thread);
14330 struct iax2_thread_list *list_head = head;
14331 struct iax2_thread *thread;
14332
14333 AST_LIST_LOCK(list_head);
14334 while ((thread = AST_LIST_REMOVE_HEAD(&idle_list, list))) {
14335 pthread_t thread_id = thread->threadid;
14336
14337 thread->stop = 1;
14338 signal_condition(&thread->lock, &thread->cond);
14339
14340 AST_LIST_UNLOCK(list_head);
14341 pthread_join(thread_id, NULL);
14342 AST_LIST_LOCK(list_head);
14343 }
14344 AST_LIST_UNLOCK(list_head);
14345 }
14346
14347 static int __unload_module(void)
14348 {
14349 struct ast_context *con;
14350 int x;
14351
14352 network_change_event_unsubscribe();
14353
14354 ast_manager_unregister("IAXpeers");
14355 ast_manager_unregister("IAXpeerlist");
14356 ast_manager_unregister("IAXnetstats");
14357 ast_manager_unregister("IAXregistry");
14358 ast_unregister_application(papp);
14359 ast_cli_unregister_multiple(cli_iax2, ARRAY_LEN(cli_iax2));
14360 ast_unregister_switch(&iax2_switch);
14361 ast_channel_unregister(&iax2_tech);
14362
14363 if (netthreadid != AST_PTHREADT_NULL) {
14364 pthread_cancel(netthreadid);
14365 pthread_kill(netthreadid, SIGURG);
14366 pthread_join(netthreadid, NULL);
14367 }
14368
14369 for (x = 0; x < ARRAY_LEN(iaxs); x++) {
14370 if (iaxs[x]) {
14371 iax2_destroy(x);
14372 }
14373 }
14374
14375
14376 cleanup_thread_list(&idle_list);
14377 cleanup_thread_list(&active_list);
14378 cleanup_thread_list(&dynamic_list);
14379
14380 ast_netsock_release(netsock);
14381 ast_netsock_release(outsock);
14382 for (x = 0; x < ARRAY_LEN(iaxs); x++) {
14383 if (iaxs[x]) {
14384 iax2_destroy(x);
14385 }
14386 }
14387 ast_manager_unregister( "IAXpeers" );
14388 ast_manager_unregister( "IAXpeerlist" );
14389 ast_manager_unregister( "IAXnetstats" );
14390 ast_manager_unregister( "IAXregistry" );
14391 ast_unregister_application(papp);
14392 #ifdef TEST_FRAMEWORK
14393 AST_TEST_UNREGISTER(test_iax2_peers_get);
14394 AST_TEST_UNREGISTER(test_iax2_users_get);
14395 #endif
14396 ast_data_unregister(NULL);
14397 ast_cli_unregister_multiple(cli_iax2, ARRAY_LEN(cli_iax2));
14398 ast_unregister_switch(&iax2_switch);
14399 ast_channel_unregister(&iax2_tech);
14400 delete_users();
14401 iax_provision_unload();
14402 reload_firmware(1);
14403
14404 for (x = 0; x < ARRAY_LEN(iaxsl); x++) {
14405 ast_mutex_destroy(&iaxsl[x]);
14406 }
14407
14408 ao2_ref(peers, -1);
14409 ao2_ref(users, -1);
14410 ao2_ref(iax_peercallno_pvts, -1);
14411 ao2_ref(iax_transfercallno_pvts, -1);
14412 ao2_ref(peercnts, -1);
14413 ao2_ref(callno_limits, -1);
14414 ao2_ref(calltoken_ignores, -1);
14415 ao2_ref(callno_pool, -1);
14416 ao2_ref(callno_pool_trunk, -1);
14417 if (timer) {
14418 ast_timer_close(timer);
14419 }
14420 transmit_processor = ast_taskprocessor_unreference(transmit_processor);
14421 sched = ast_sched_thread_destroy(sched);
14422
14423 con = ast_context_find(regcontext);
14424 if (con)
14425 ast_context_destroy(con, "IAX2");
14426 ast_unload_realtime("iaxpeers");
14427 return 0;
14428 }
14429
14430 static int unload_module(void)
14431 {
14432 ast_custom_function_unregister(&iaxpeer_function);
14433 ast_custom_function_unregister(&iaxvar_function);
14434 return __unload_module();
14435 }
14436
14437 static int peer_set_sock_cb(void *obj, void *arg, int flags)
14438 {
14439 struct iax2_peer *peer = obj;
14440
14441 if (peer->sockfd < 0)
14442 peer->sockfd = defaultsockfd;
14443
14444 return 0;
14445 }
14446
14447 static int pvt_hash_cb(const void *obj, const int flags)
14448 {
14449 const struct chan_iax2_pvt *pvt = obj;
14450
14451 return pvt->peercallno;
14452 }
14453
14454 static int pvt_cmp_cb(void *obj, void *arg, int flags)
14455 {
14456 struct chan_iax2_pvt *pvt = obj, *pvt2 = arg;
14457
14458
14459
14460
14461 return match(&pvt2->addr, pvt2->peercallno, pvt2->callno, pvt,
14462 pvt2->frames_received) ? CMP_MATCH | CMP_STOP : 0;
14463 }
14464
14465 static int transfercallno_pvt_hash_cb(const void *obj, const int flags)
14466 {
14467 const struct chan_iax2_pvt *pvt = obj;
14468
14469 return pvt->transfercallno;
14470 }
14471
14472 static int transfercallno_pvt_cmp_cb(void *obj, void *arg, int flags)
14473 {
14474 struct chan_iax2_pvt *pvt = obj, *pvt2 = arg;
14475
14476
14477
14478
14479 return match(&pvt2->transfer, pvt2->transfercallno, pvt2->callno, pvt,
14480 pvt2->frames_received) ? CMP_MATCH | CMP_STOP : 0;
14481 }
14482
14483 static int load_objects(void)
14484 {
14485 peers = users = iax_peercallno_pvts = iax_transfercallno_pvts = NULL;
14486 peercnts = callno_limits = calltoken_ignores = callno_pool = callno_pool_trunk = NULL;
14487
14488 if (!(peers = ao2_container_alloc(MAX_PEER_BUCKETS, peer_hash_cb, peer_cmp_cb))) {
14489 goto container_fail;
14490 } else if (!(users = ao2_container_alloc(MAX_USER_BUCKETS, user_hash_cb, user_cmp_cb))) {
14491 goto container_fail;
14492 } else if (!(iax_peercallno_pvts = ao2_container_alloc(IAX_MAX_CALLS, pvt_hash_cb, pvt_cmp_cb))) {
14493 goto container_fail;
14494 } else if (!(iax_transfercallno_pvts = ao2_container_alloc(IAX_MAX_CALLS, transfercallno_pvt_hash_cb, transfercallno_pvt_cmp_cb))) {
14495 goto container_fail;
14496 } else if (!(peercnts = ao2_container_alloc(MAX_PEER_BUCKETS, peercnt_hash_cb, peercnt_cmp_cb))) {
14497 goto container_fail;
14498 } else if (!(callno_limits = ao2_container_alloc(MAX_PEER_BUCKETS, addr_range_hash_cb, addr_range_cmp_cb))) {
14499 goto container_fail;
14500 } else if (!(calltoken_ignores = ao2_container_alloc(MAX_PEER_BUCKETS, addr_range_hash_cb, addr_range_cmp_cb))) {
14501 goto container_fail;
14502 } else if (create_callno_pools()) {
14503 goto container_fail;
14504 } else if (!(transmit_processor = ast_taskprocessor_get("iax2_transmit", TPS_REF_DEFAULT))) {
14505 goto container_fail;
14506 }
14507
14508 return 0;
14509
14510 container_fail:
14511 if (peers) {
14512 ao2_ref(peers, -1);
14513 }
14514 if (users) {
14515 ao2_ref(users, -1);
14516 }
14517 if (iax_peercallno_pvts) {
14518 ao2_ref(iax_peercallno_pvts, -1);
14519 }
14520 if (iax_transfercallno_pvts) {
14521 ao2_ref(iax_transfercallno_pvts, -1);
14522 }
14523 if (peercnts) {
14524 ao2_ref(peercnts, -1);
14525 }
14526 if (callno_limits) {
14527 ao2_ref(callno_limits, -1);
14528 }
14529 if (calltoken_ignores) {
14530 ao2_ref(calltoken_ignores, -1);
14531 }
14532 if (callno_pool) {
14533 ao2_ref(callno_pool, -1);
14534 }
14535 if (callno_pool_trunk) {
14536 ao2_ref(callno_pool_trunk, -1);
14537 }
14538 return AST_MODULE_LOAD_FAILURE;
14539 }
14540
14541
14542 #define DATA_EXPORT_IAX2_PEER(MEMBER) \
14543 MEMBER(iax2_peer, name, AST_DATA_STRING) \
14544 MEMBER(iax2_peer, username, AST_DATA_STRING) \
14545 MEMBER(iax2_peer, secret, AST_DATA_PASSWORD) \
14546 MEMBER(iax2_peer, dbsecret, AST_DATA_PASSWORD) \
14547 MEMBER(iax2_peer, outkey, AST_DATA_STRING) \
14548 MEMBER(iax2_peer, regexten, AST_DATA_STRING) \
14549 MEMBER(iax2_peer, context, AST_DATA_STRING) \
14550 MEMBER(iax2_peer, peercontext, AST_DATA_STRING) \
14551 MEMBER(iax2_peer, mailbox, AST_DATA_STRING) \
14552 MEMBER(iax2_peer, mohinterpret, AST_DATA_STRING) \
14553 MEMBER(iax2_peer, mohsuggest, AST_DATA_STRING) \
14554 MEMBER(iax2_peer, inkeys, AST_DATA_STRING) \
14555 MEMBER(iax2_peer, cid_num, AST_DATA_STRING) \
14556 MEMBER(iax2_peer, cid_name, AST_DATA_STRING) \
14557 MEMBER(iax2_peer, zonetag, AST_DATA_STRING) \
14558 MEMBER(iax2_peer, parkinglot, AST_DATA_STRING) \
14559 MEMBER(iax2_peer, expiry, AST_DATA_SECONDS) \
14560 MEMBER(iax2_peer, callno, AST_DATA_INTEGER) \
14561 MEMBER(iax2_peer, lastms, AST_DATA_MILLISECONDS) \
14562 MEMBER(iax2_peer, maxms, AST_DATA_MILLISECONDS) \
14563 MEMBER(iax2_peer, pokefreqok, AST_DATA_MILLISECONDS) \
14564 MEMBER(iax2_peer, pokefreqnotok, AST_DATA_MILLISECONDS) \
14565 MEMBER(iax2_peer, historicms, AST_DATA_INTEGER) \
14566 MEMBER(iax2_peer, smoothing, AST_DATA_BOOLEAN) \
14567 MEMBER(iax2_peer, maxcallno, AST_DATA_INTEGER)
14568
14569 AST_DATA_STRUCTURE(iax2_peer, DATA_EXPORT_IAX2_PEER);
14570
14571 static int peers_data_provider_get(const struct ast_data_search *search,
14572 struct ast_data *data_root)
14573 {
14574 struct ast_data *data_peer;
14575 struct iax2_peer *peer;
14576 struct ao2_iterator i;
14577 char status[20];
14578 struct ast_str *encmethods = ast_str_alloca(256);
14579
14580 i = ao2_iterator_init(peers, 0);
14581 while ((peer = ao2_iterator_next(&i))) {
14582 data_peer = ast_data_add_node(data_root, "peer");
14583 if (!data_peer) {
14584 peer_unref(peer);
14585 continue;
14586 }
14587
14588 ast_data_add_structure(iax2_peer, data_peer, peer);
14589
14590 ast_data_add_codecs(data_peer, "codecs", peer->capability);
14591
14592 peer_status(peer, status, sizeof(status));
14593 ast_data_add_str(data_peer, "status", status);
14594
14595 ast_data_add_str(data_peer, "host", ast_sockaddr_stringify_host(&peer->addr));
14596
14597 ast_data_add_str(data_peer, "mask", ast_inet_ntoa(peer->mask));
14598
14599 ast_data_add_int(data_peer, "port", ast_sockaddr_port(&peer->addr));
14600
14601 ast_data_add_bool(data_peer, "trunk", ast_test_flag64(peer, IAX_TRUNK));
14602
14603 ast_data_add_bool(data_peer, "dynamic", ast_test_flag64(peer, IAX_DYNAMIC));
14604
14605 encmethods_to_str(peer->encmethods, encmethods);
14606 ast_data_add_str(data_peer, "encryption", peer->encmethods ? ast_str_buffer(encmethods) : "no");
14607
14608 peer_unref(peer);
14609
14610 if (!ast_data_search_match(search, data_peer)) {
14611 ast_data_remove_node(data_root, data_peer);
14612 }
14613 }
14614 ao2_iterator_destroy(&i);
14615
14616 return 0;
14617 }
14618
14619 #define DATA_EXPORT_IAX2_USER(MEMBER) \
14620 MEMBER(iax2_user, name, AST_DATA_STRING) \
14621 MEMBER(iax2_user, dbsecret, AST_DATA_PASSWORD) \
14622 MEMBER(iax2_user, accountcode, AST_DATA_STRING) \
14623 MEMBER(iax2_user, mohinterpret, AST_DATA_STRING) \
14624 MEMBER(iax2_user, mohsuggest, AST_DATA_STRING) \
14625 MEMBER(iax2_user, inkeys, AST_DATA_STRING) \
14626 MEMBER(iax2_user, language, AST_DATA_STRING) \
14627 MEMBER(iax2_user, cid_num, AST_DATA_STRING) \
14628 MEMBER(iax2_user, cid_name, AST_DATA_STRING) \
14629 MEMBER(iax2_user, parkinglot, AST_DATA_STRING) \
14630 MEMBER(iax2_user, maxauthreq, AST_DATA_INTEGER) \
14631 MEMBER(iax2_user, curauthreq, AST_DATA_INTEGER)
14632
14633 AST_DATA_STRUCTURE(iax2_user, DATA_EXPORT_IAX2_USER);
14634
14635 static int users_data_provider_get(const struct ast_data_search *search,
14636 struct ast_data *data_root)
14637 {
14638 struct ast_data *data_user, *data_authmethods, *data_enum_node;
14639 struct iax2_user *user;
14640 struct ao2_iterator i;
14641 char auth[90];
14642 char *pstr = "";
14643
14644 i = ao2_iterator_init(users, 0);
14645 for (; (user = ao2_iterator_next(&i)); user_unref(user)) {
14646 data_user = ast_data_add_node(data_root, "user");
14647 if (!data_user) {
14648 continue;
14649 }
14650
14651 ast_data_add_structure(iax2_user, data_user, user);
14652
14653 ast_data_add_codecs(data_user, "codecs", user->capability);
14654
14655 if (!ast_strlen_zero(user->secret)) {
14656 ast_copy_string(auth, user->secret, sizeof(auth));
14657 } else if (!ast_strlen_zero(user->inkeys)) {
14658 snprintf(auth, sizeof(auth), "Key: %s", user->inkeys);
14659 } else {
14660 ast_copy_string(auth, "no secret", sizeof(auth));
14661 }
14662 ast_data_add_password(data_user, "secret", auth);
14663
14664 ast_data_add_str(data_user, "context", user->contexts ? user->contexts->context : DEFAULT_CONTEXT);
14665
14666
14667 data_authmethods = ast_data_add_node(data_user, "authmethods");
14668 if (!data_authmethods) {
14669 ast_data_remove_node(data_root, data_user);
14670 continue;
14671 }
14672 ast_data_add_bool(data_authmethods, "rsa", user->authmethods & IAX_AUTH_RSA);
14673 ast_data_add_bool(data_authmethods, "md5", user->authmethods & IAX_AUTH_MD5);
14674 ast_data_add_bool(data_authmethods, "plaintext", user->authmethods & IAX_AUTH_PLAINTEXT);
14675
14676
14677 data_enum_node = ast_data_add_node(data_user, "amaflags");
14678 if (!data_enum_node) {
14679 ast_data_remove_node(data_root, data_user);
14680 continue;
14681 }
14682 ast_data_add_int(data_enum_node, "value", user->amaflags);
14683 ast_data_add_str(data_enum_node, "text", ast_cdr_flags2str(user->amaflags));
14684
14685 ast_data_add_bool(data_user, "access-control", user->ha ? 1 : 0);
14686
14687 if (ast_test_flag64(user, IAX_CODEC_NOCAP)) {
14688 pstr = "REQ only";
14689 } else if (ast_test_flag64(user, IAX_CODEC_NOPREFS)) {
14690 pstr = "disabled";
14691 } else {
14692 pstr = ast_test_flag64(user, IAX_CODEC_USER_FIRST) ? "caller" : "host";
14693 }
14694 ast_data_add_str(data_user, "codec-preferences", pstr);
14695
14696 if (!ast_data_search_match(search, data_user)) {
14697 ast_data_remove_node(data_root, data_user);
14698 }
14699 }
14700 ao2_iterator_destroy(&i);
14701
14702 return 0;
14703 }
14704
14705 static const struct ast_data_handler peers_data_provider = {
14706 .version = AST_DATA_HANDLER_VERSION,
14707 .get = peers_data_provider_get
14708 };
14709
14710 static const struct ast_data_handler users_data_provider = {
14711 .version = AST_DATA_HANDLER_VERSION,
14712 .get = users_data_provider_get
14713 };
14714
14715 static const struct ast_data_entry iax2_data_providers[] = {
14716 AST_DATA_ENTRY("asterisk/channel/iax2/peers", &peers_data_provider),
14717 AST_DATA_ENTRY("asterisk/channel/iax2/users", &users_data_provider),
14718 };
14719
14720
14721 static int load_module(void)
14722 {
14723 static const char config[] = "iax.conf";
14724 int x = 0;
14725 struct iax2_registry *reg = NULL;
14726
14727 if (load_objects()) {
14728 return AST_MODULE_LOAD_FAILURE;
14729 }
14730
14731 memset(iaxs, 0, sizeof(iaxs));
14732
14733 for (x = 0; x < ARRAY_LEN(iaxsl); x++) {
14734 ast_mutex_init(&iaxsl[x]);
14735 }
14736
14737 if (!(sched = ast_sched_thread_create())) {
14738 ast_log(LOG_ERROR, "Failed to create scheduler thread\n");
14739 return AST_MODULE_LOAD_FAILURE;
14740 }
14741
14742 if (!(io = io_context_create())) {
14743 ast_log(LOG_ERROR, "Failed to create I/O context\n");
14744 sched = ast_sched_thread_destroy(sched);
14745 return AST_MODULE_LOAD_FAILURE;
14746 }
14747
14748 if (!(netsock = ast_netsock_list_alloc())) {
14749 ast_log(LOG_ERROR, "Failed to create netsock list\n");
14750 io_context_destroy(io);
14751 sched = ast_sched_thread_destroy(sched);
14752 return AST_MODULE_LOAD_FAILURE;
14753 }
14754 ast_netsock_init(netsock);
14755
14756 outsock = ast_netsock_list_alloc();
14757 if (!outsock) {
14758 ast_log(LOG_ERROR, "Could not allocate outsock list.\n");
14759 io_context_destroy(io);
14760 sched = ast_sched_thread_destroy(sched);
14761 return AST_MODULE_LOAD_FAILURE;
14762 }
14763 ast_netsock_init(outsock);
14764
14765 randomcalltokendata = ast_random();
14766
14767 iax_set_output(iax_debug_output);
14768 iax_set_error(iax_error_output);
14769 jb_setoutput(jb_error_output, jb_warning_output, NULL);
14770
14771 if ((timer = ast_timer_open())) {
14772 ast_timer_set_rate(timer, 1000 / trunkfreq);
14773 }
14774
14775 if (set_config(config, 0) == -1) {
14776 if (timer) {
14777 ast_timer_close(timer);
14778 }
14779 return AST_MODULE_LOAD_DECLINE;
14780 }
14781
14782 #ifdef TEST_FRAMEWORK
14783 AST_TEST_REGISTER(test_iax2_peers_get);
14784 AST_TEST_REGISTER(test_iax2_users_get);
14785 #endif
14786
14787
14788 ast_data_register_multiple(iax2_data_providers, ARRAY_LEN(iax2_data_providers));
14789 ast_cli_register_multiple(cli_iax2, ARRAY_LEN(cli_iax2));
14790
14791 ast_register_application_xml(papp, iax2_prov_app);
14792
14793 ast_custom_function_register(&iaxpeer_function);
14794 ast_custom_function_register(&iaxvar_function);
14795
14796 ast_manager_register_xml("IAXpeers", EVENT_FLAG_SYSTEM | EVENT_FLAG_REPORTING, manager_iax2_show_peers);
14797 ast_manager_register_xml("IAXpeerlist", EVENT_FLAG_SYSTEM | EVENT_FLAG_REPORTING, manager_iax2_show_peer_list);
14798 ast_manager_register_xml("IAXnetstats", EVENT_FLAG_SYSTEM | EVENT_FLAG_REPORTING, manager_iax2_show_netstats);
14799 ast_manager_register_xml("IAXregistry", EVENT_FLAG_SYSTEM | EVENT_FLAG_REPORTING, manager_iax2_show_registry);
14800
14801 if (ast_channel_register(&iax2_tech)) {
14802 ast_log(LOG_ERROR, "Unable to register channel class %s\n", "IAX2");
14803 __unload_module();
14804 return AST_MODULE_LOAD_FAILURE;
14805 }
14806
14807 if (ast_register_switch(&iax2_switch)) {
14808 ast_log(LOG_ERROR, "Unable to register IAX switch\n");
14809 }
14810
14811 if (start_network_thread()) {
14812 ast_log(LOG_ERROR, "Unable to start network thread\n");
14813 __unload_module();
14814 return AST_MODULE_LOAD_FAILURE;
14815 } else {
14816 ast_verb(2, "IAX Ready and Listening\n");
14817 }
14818
14819 AST_LIST_LOCK(®istrations);
14820 AST_LIST_TRAVERSE(®istrations, reg, entry)
14821 iax2_do_register(reg);
14822 AST_LIST_UNLOCK(®istrations);
14823
14824 ao2_callback(peers, 0, peer_set_sock_cb, NULL);
14825 ao2_callback(peers, 0, iax2_poke_peer_cb, NULL);
14826
14827
14828 reload_firmware(0);
14829 iax_provision_reload(0);
14830
14831 ast_realtime_require_field("iaxpeers", "name", RQ_CHAR, 10, "ipaddr", RQ_CHAR, 15, "port", RQ_UINTEGER2, 5, "regseconds", RQ_UINTEGER2, 6, SENTINEL);
14832
14833 network_change_event_subscribe();
14834
14835 return AST_MODULE_LOAD_SUCCESS;
14836 }
14837
14838 AST_MODULE_INFO(ASTERISK_GPL_KEY, AST_MODFLAG_LOAD_ORDER, "Inter Asterisk eXchange (Ver 2)",
14839 .load = load_module,
14840 .unload = unload_module,
14841 .reload = reload,
14842 .load_pri = AST_MODPRI_CHANNEL_DRIVER,
14843 .nonoptreq = "res_crypto",
14844 );