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 #include <sys/socket.h>
00035 #include <sys/signal.h>
00036 #include <sys/param.h>
00037 #if defined(BSD)
00038 #ifndef IPTOS_MINCOST
00039 #define IPTOS_MINCOST 0x02
00040 #endif
00041 #endif
00042 #include <arpa/inet.h>
00043 #include <net/if.h>
00044 #include <netinet/in.h>
00045 #include <netinet/in_systm.h>
00046 #include <netinet/ip.h>
00047 #include <unistd.h>
00048 #include <stdlib.h>
00049 #include <netdb.h>
00050 #include <stdio.h>
00051 #include <string.h>
00052 #include <errno.h>
00053 #include <fcntl.h>
00054 #ifdef __cplusplus
00055 extern "C" {
00056 #endif
00057
00058 #include "asterisk.h"
00059
00060 ASTERISK_FILE_VERSION(__FILE__, "$Revision: 211526 $")
00061
00062 #include "asterisk/lock.h"
00063 #include "asterisk/logger.h"
00064 #include "asterisk/channel.h"
00065 #include "asterisk/config.h"
00066 #include "asterisk/module.h"
00067 #include "asterisk/pbx.h"
00068 #include "asterisk/options.h"
00069 #include "asterisk/utils.h"
00070 #include "asterisk/lock.h"
00071 #include "asterisk/sched.h"
00072 #include "asterisk/io.h"
00073 #include "asterisk/rtp.h"
00074 #include "asterisk/acl.h"
00075 #include "asterisk/callerid.h"
00076 #include "asterisk/cli.h"
00077 #include "asterisk/dsp.h"
00078 #include "asterisk/causes.h"
00079 #ifdef __cplusplus
00080 }
00081 #endif
00082 #include "h323/chan_h323.h"
00083
00084 send_digit_cb on_send_digit;
00085 on_rtp_cb on_external_rtp_create;
00086 start_rtp_cb on_start_rtp_channel;
00087 setup_incoming_cb on_incoming_call;
00088 setup_outbound_cb on_outgoing_call;
00089 chan_ringing_cb on_chan_ringing;
00090 con_established_cb on_connection_established;
00091 clear_con_cb on_connection_cleared;
00092 answer_call_cb on_answer_call;
00093 progress_cb on_progress;
00094 rfc2833_cb on_set_rfc2833_payload;
00095 hangup_cb on_hangup;
00096 setcapabilities_cb on_setcapabilities;
00097
00098
00099 int h323debug;
00100
00101
00102 static const char type[] = "H323";
00103 static const char desc[] = "The NuFone Network's Open H.323 Channel Driver";
00104 static const char tdesc[] = "The NuFone Network's Open H.323 Channel Driver";
00105 static const char config[] = "h323.conf";
00106 static char default_context[AST_MAX_CONTEXT] = "default";
00107 static struct sockaddr_in bindaddr;
00108
00109
00110 static int h323_signalling_port = 1720;
00111 static char gatekeeper[100];
00112 static int gatekeeper_disable = 1;
00113 static int gatekeeper_discover = 0;
00114 static int usingGk = 0;
00115 static int gkroute = 0;
00116
00117 static int userbyalias = 1;
00118 static int tos = 0;
00119 static char secret[50];
00120 static unsigned int unique = 0;
00121
00122 static call_options_t global_options;
00123
00124
00125 struct oh323_pvt {
00126 ast_mutex_t lock;
00127 call_options_t options;
00128 int alreadygone;
00129 int needdestroy;
00130 call_details_t cd;
00131 struct ast_channel *owner;
00132 struct sockaddr_in sa;
00133 struct sockaddr_in redirip;
00134 int nonCodecCapability;
00135 int outgoing;
00136 char exten[AST_MAX_EXTENSION];
00137 char context[AST_MAX_CONTEXT];
00138 char accountcode[256];
00139 char cid_num[80];
00140 char cid_name[80];
00141 char rdnis[80];
00142 int amaflags;
00143 struct ast_rtp *rtp;
00144 struct ast_dsp *vad;
00145 int nativeformats;
00146 int needhangup;
00147 int hangupcause;
00148 int newstate;
00149 int newcontrol;
00150 struct oh323_pvt *next;
00151 } *iflist = NULL;
00152
00153 static struct ast_user_list {
00154 struct oh323_user *users;
00155 ast_mutex_t lock;
00156 } userl;
00157
00158 static struct ast_peer_list {
00159 struct oh323_peer *peers;
00160 ast_mutex_t lock;
00161 } peerl;
00162
00163 static struct ast_alias_list {
00164 struct oh323_alias *aliases;
00165 ast_mutex_t lock;
00166 } aliasl;
00167
00168
00169 static struct sched_context *sched;
00170 static struct io_context *io;
00171
00172
00173 AST_MUTEX_DEFINE_STATIC(iflock);
00174
00175
00176 static int usecnt = 0;
00177 AST_MUTEX_DEFINE_STATIC(usecnt_lock);
00178
00179
00180
00181 AST_MUTEX_DEFINE_STATIC(monlock);
00182
00183
00184 AST_MUTEX_DEFINE_STATIC(caplock);
00185
00186
00187 AST_MUTEX_DEFINE_STATIC(h323_reload_lock);
00188 static int h323_reloading = 0;
00189
00190
00191
00192 static pthread_t monitor_thread = AST_PTHREADT_NULL;
00193 static int restart_monitor(void);
00194 static int h323_do_reload(void);
00195
00196 static struct ast_channel *oh323_request(const char *type, int format, void *data, int *cause);
00197 static int oh323_digit(struct ast_channel *c, char digit);
00198 static int oh323_call(struct ast_channel *c, char *dest, int timeout);
00199 static int oh323_hangup(struct ast_channel *c);
00200 static int oh323_answer(struct ast_channel *c);
00201 static struct ast_frame *oh323_read(struct ast_channel *c);
00202 static int oh323_write(struct ast_channel *c, struct ast_frame *frame);
00203 static int oh323_indicate(struct ast_channel *c, int condition);
00204 static int oh323_fixup(struct ast_channel *oldchan, struct ast_channel *newchan);
00205
00206 static const struct ast_channel_tech oh323_tech = {
00207 .type = type,
00208 .description = tdesc,
00209 .capabilities = AST_FORMAT_ULAW,
00210 .properties = AST_CHAN_TP_WANTSJITTER,
00211 .requester = oh323_request,
00212 .send_digit = oh323_digit,
00213 .call = oh323_call,
00214 .hangup = oh323_hangup,
00215 .answer = oh323_answer,
00216 .read = oh323_read,
00217 .write = oh323_write,
00218 .indicate = oh323_indicate,
00219 .fixup = oh323_fixup,
00220
00221 #if 0
00222 .bridge = ast_rtp_bridge,
00223 #endif
00224 };
00225
00226
00227 static void __oh323_update_info(struct ast_channel *c, struct oh323_pvt *pvt)
00228 {
00229 if (c->nativeformats != pvt->nativeformats) {
00230 if (h323debug)
00231 ast_log(LOG_DEBUG, "Preparing %s for new native format\n", c->name);
00232 c->nativeformats = pvt->nativeformats;
00233 ast_set_read_format(c, c->readformat);
00234 ast_set_write_format(c, c->writeformat);
00235 }
00236 if (pvt->needhangup) {
00237 if (h323debug)
00238 ast_log(LOG_DEBUG, "Process pending hangup for %s\n", c->name);
00239 c->_softhangup |= AST_SOFTHANGUP_DEV;
00240 c->hangupcause = pvt->hangupcause;
00241 ast_queue_hangup(c);
00242 pvt->needhangup = 0;
00243 pvt->newstate = pvt->newcontrol = -1;
00244 }
00245 if (pvt->newstate >= 0) {
00246 ast_setstate(c, pvt->newstate);
00247 pvt->newstate = -1;
00248 }
00249 if (pvt->newcontrol >= 0) {
00250 ast_queue_control(c, pvt->newcontrol);
00251 pvt->newcontrol = -1;
00252 }
00253 }
00254
00255
00256 static void oh323_update_info(struct ast_channel *c)
00257 {
00258 struct oh323_pvt *pvt = c->tech_pvt;
00259
00260 if (pvt) {
00261 ast_mutex_lock(&pvt->lock);
00262 __oh323_update_info(c, pvt);
00263 ast_mutex_unlock(&pvt->lock);
00264 }
00265 }
00266
00267 static void cleanup_call_details(call_details_t *cd)
00268 {
00269 if (cd->call_token) {
00270 free(cd->call_token);
00271 cd->call_token = NULL;
00272 }
00273 if (cd->call_source_aliases) {
00274 free(cd->call_source_aliases);
00275 cd->call_source_aliases = NULL;
00276 }
00277 if (cd->call_dest_alias) {
00278 free(cd->call_dest_alias);
00279 cd->call_dest_alias = NULL;
00280 }
00281 if (cd->call_source_name) {
00282 free(cd->call_source_name);
00283 cd->call_source_name = NULL;
00284 }
00285 if (cd->call_source_e164) {
00286 free(cd->call_source_e164);
00287 cd->call_source_e164 = NULL;
00288 }
00289 if (cd->call_dest_e164) {
00290 free(cd->call_dest_e164);
00291 cd->call_dest_e164 = NULL;
00292 }
00293 if (cd->sourceIp) {
00294 free(cd->sourceIp);
00295 cd->sourceIp = NULL;
00296 }
00297 }
00298
00299 static void __oh323_destroy(struct oh323_pvt *pvt)
00300 {
00301 struct oh323_pvt *cur, *prev = NULL;
00302
00303 if (pvt->rtp) {
00304 ast_rtp_destroy(pvt->rtp);
00305 }
00306
00307
00308 if (pvt->vad) {
00309 ast_dsp_free(pvt->vad);
00310 }
00311 cleanup_call_details(&pvt->cd);
00312
00313
00314 if (pvt->owner) {
00315 ast_mutex_lock(&pvt->owner->lock);
00316 ast_log(LOG_DEBUG, "Detaching from %s\n", pvt->owner->name);
00317 pvt->owner->tech_pvt = NULL;
00318 ast_mutex_unlock(&pvt->owner->lock);
00319 }
00320 cur = iflist;
00321 while(cur) {
00322 if (cur == pvt) {
00323 if (prev)
00324 prev->next = cur->next;
00325 else
00326 iflist = cur->next;
00327 break;
00328 }
00329 prev = cur;
00330 cur = cur->next;
00331 }
00332 if (!cur) {
00333 ast_log(LOG_WARNING, "%p is not in list?!?! \n", cur);
00334 } else {
00335 ast_mutex_destroy(&pvt->lock);
00336 free(pvt);
00337 }
00338 }
00339
00340 static void oh323_destroy(struct oh323_pvt *pvt)
00341 {
00342 ast_mutex_lock(&iflock);
00343 __oh323_destroy(pvt);
00344 ast_mutex_unlock(&iflock);
00345 }
00346
00347
00348
00349
00350
00351 static int oh323_digit(struct ast_channel *c, char digit)
00352 {
00353 struct oh323_pvt *pvt = (struct oh323_pvt *) c->tech_pvt;
00354 char *token;
00355
00356 if (!pvt) {
00357 ast_log(LOG_ERROR, "No private structure?! This is bad\n");
00358 return -1;
00359 }
00360 ast_mutex_lock(&pvt->lock);
00361 if (pvt->rtp && (pvt->options.dtmfmode & H323_DTMF_RFC2833)) {
00362
00363 if (h323debug) {
00364 ast_log(LOG_DEBUG, "Sending out-of-band digit %c on %s\n", digit, c->name);
00365 }
00366 ast_rtp_senddigit(pvt->rtp, digit);
00367 } else {
00368
00369 if (h323debug) {
00370 ast_log(LOG_DEBUG, "Sending inband digit %c on %s\n", digit, c->name);
00371 }
00372 token = pvt->cd.call_token ? strdup(pvt->cd.call_token) : NULL;
00373 h323_send_tone(token, digit);
00374 if (token) {
00375 free(token);
00376 }
00377 }
00378 ast_mutex_unlock(&pvt->lock);
00379 oh323_update_info(c);
00380 return 0;
00381 }
00382
00383
00384
00385
00386
00387
00388 static int oh323_call(struct ast_channel *c, char *dest, int timeout)
00389 {
00390 int res = 0;
00391 struct oh323_pvt *pvt = (struct oh323_pvt *)c->tech_pvt;
00392 char addr[INET_ADDRSTRLEN];
00393 char called_addr[1024];
00394
00395 if (h323debug) {
00396 ast_log(LOG_DEBUG, "Calling to %s on %s\n", dest, c->name);
00397 }
00398 if ((c->_state != AST_STATE_DOWN) && (c->_state != AST_STATE_RESERVED)) {
00399 ast_log(LOG_WARNING, "Line is already in use (%s)\n", c->name);
00400 return -1;
00401 }
00402 ast_mutex_lock(&pvt->lock);
00403 if (usingGk) {
00404 if (ast_strlen_zero(pvt->exten)) {
00405 strncpy(called_addr, dest, sizeof(called_addr));
00406 } else {
00407 snprintf(called_addr, sizeof(called_addr), "%s@%s", pvt->exten, dest);
00408 }
00409 } else {
00410 ast_inet_ntoa(addr, sizeof(addr), pvt->sa.sin_addr);
00411 res = htons(pvt->sa.sin_port);
00412 if (ast_strlen_zero(pvt->exten)) {
00413 snprintf(called_addr, sizeof(called_addr), "%s:%d", addr, res);
00414 } else {
00415 snprintf(called_addr, sizeof(called_addr), "%s@%s:%d", pvt->exten, addr, res);
00416 }
00417 }
00418
00419 called_addr[sizeof(called_addr) - 1] = '\0';
00420
00421 if (c->cid.cid_num) {
00422 strncpy(pvt->options.cid_num, c->cid.cid_num, sizeof(pvt->options.cid_num));
00423 }
00424 if (c->cid.cid_name) {
00425 strncpy(pvt->options.cid_name, c->cid.cid_name, sizeof(pvt->options.cid_name));
00426 }
00427
00428
00429 pvt->outgoing = 1;
00430
00431 ast_log(LOG_DEBUG, "Placing outgoing call to %s, %d\n", called_addr, pvt->options.dtmfcodec);
00432 ast_mutex_unlock(&pvt->lock);
00433 res = h323_make_call(called_addr, &(pvt->cd), &pvt->options);
00434 if (res) {
00435 ast_log(LOG_NOTICE, "h323_make_call failed(%s)\n", c->name);
00436 return -1;
00437 }
00438 oh323_update_info(c);
00439 return 0;
00440 }
00441
00442 static int oh323_answer(struct ast_channel *c)
00443 {
00444 int res;
00445 struct oh323_pvt *pvt = (struct oh323_pvt *) c->tech_pvt;
00446 char *token;
00447
00448 if (h323debug)
00449 ast_log(LOG_DEBUG, "Answering on %s\n", c->name);
00450
00451 ast_mutex_lock(&pvt->lock);
00452 token = pvt->cd.call_token ? strdup(pvt->cd.call_token) : NULL;
00453 ast_mutex_unlock(&pvt->lock);
00454 res = h323_answering_call(token, 0);
00455 if (token)
00456 free(token);
00457
00458 oh323_update_info(c);
00459 if (c->_state != AST_STATE_UP) {
00460 ast_setstate(c, AST_STATE_UP);
00461 }
00462 return res;
00463 }
00464
00465 static int oh323_hangup(struct ast_channel *c)
00466 {
00467 struct oh323_pvt *pvt = (struct oh323_pvt *) c->tech_pvt;
00468 int needcancel = 0;
00469 int q931cause = AST_CAUSE_NORMAL_CLEARING;
00470 char *call_token;
00471
00472
00473 if (h323debug)
00474 ast_log(LOG_DEBUG, "Hanging up call %s\n", c->name);
00475
00476 if (!c->tech_pvt) {
00477 ast_log(LOG_DEBUG, "Asked to hangup channel not connected\n");
00478 return 0;
00479 }
00480 ast_mutex_lock(&pvt->lock);
00481
00482 if (pvt->owner != c) {
00483 ast_log(LOG_WARNING, "Huh? We aren't the owner?\n");
00484 ast_mutex_unlock(&pvt->lock);
00485 return 0;
00486 }
00487 if (!c || (c->_state != AST_STATE_UP)) {
00488 needcancel = 1;
00489 }
00490
00491 pvt->owner = NULL;
00492 c->tech_pvt = NULL;
00493
00494 if (c->hangupcause) {
00495 q931cause = c->hangupcause;
00496 } else {
00497 char *cause = pbx_builtin_getvar_helper(c, "DIALSTATUS");
00498 if (cause) {
00499 if (!strcmp(cause, "CONGESTION")) {
00500 q931cause = AST_CAUSE_NORMAL_CIRCUIT_CONGESTION;
00501 } else if (!strcmp(cause, "BUSY")) {
00502 q931cause = AST_CAUSE_USER_BUSY;
00503 } else if (!strcmp(cause, "CHANISUNVAIL")) {
00504 q931cause = AST_CAUSE_REQUESTED_CHAN_UNAVAIL;
00505 } else if (!strcmp(cause, "NOANSWER")) {
00506 q931cause = AST_CAUSE_NO_ANSWER;
00507 } else if (!strcmp(cause, "CANCEL")) {
00508 q931cause = AST_CAUSE_CALL_REJECTED;
00509 }
00510 }
00511 }
00512
00513
00514 if (!pvt->alreadygone && !pvt->hangupcause) {
00515 call_token = pvt->cd.call_token ? strdup(pvt->cd.call_token) : NULL;
00516 if (call_token) {
00517
00518 ast_mutex_unlock(&pvt->lock);
00519 if (h323_clear_call(call_token, q931cause)) {
00520 ast_log(LOG_DEBUG, "ClearCall failed.\n");
00521 }
00522 free(call_token);
00523 ast_mutex_lock(&pvt->lock);
00524 }
00525 }
00526 pvt->needdestroy = 1;
00527
00528
00529 ast_mutex_lock(&usecnt_lock);
00530 usecnt--;
00531 if (usecnt < 0) {
00532 ast_log(LOG_WARNING, "Usecnt < 0\n");
00533 }
00534 ast_mutex_unlock(&usecnt_lock);
00535 ast_mutex_unlock(&pvt->lock);
00536 ast_update_use_count();
00537 return 0;
00538 }
00539
00540 static struct ast_frame *oh323_rtp_read(struct oh323_pvt *pvt)
00541 {
00542
00543 struct ast_frame *f;
00544 static struct ast_frame null_frame = { AST_FRAME_NULL, };
00545
00546
00547 if (pvt->options.nat) {
00548 ast_rtp_setnat(pvt->rtp, pvt->options.nat);
00549 pvt->options.nat = 0;
00550 }
00551
00552 f = ast_rtp_read(pvt->rtp);
00553
00554 if (f && (f->frametype == AST_FRAME_DTMF) && !(pvt->options.dtmfmode & H323_DTMF_RFC2833)) {
00555 return &null_frame;
00556 }
00557 if (pvt->owner) {
00558
00559 if (f->frametype == AST_FRAME_VOICE) {
00560 if (f->subclass != pvt->owner->nativeformats) {
00561
00562 if (ast_mutex_trylock(&pvt->owner->lock)) {
00563 ast_log(LOG_NOTICE, "Format changed but channel is locked. Ignoring frame...\n");
00564 return &null_frame;
00565 }
00566 ast_log(LOG_DEBUG, "Oooh, format changed to %d\n", f->subclass);
00567 pvt->owner->nativeformats = f->subclass;
00568 pvt->nativeformats = f->subclass;
00569 ast_set_read_format(pvt->owner, pvt->owner->readformat);
00570 ast_set_write_format(pvt->owner, pvt->owner->writeformat);
00571 ast_mutex_unlock(&pvt->owner->lock);
00572 }
00573
00574 if ((pvt->options.dtmfmode & H323_DTMF_INBAND) && pvt->vad) {
00575 if (!ast_mutex_trylock(&pvt->owner->lock)) {
00576 f = ast_dsp_process(pvt->owner,pvt->vad,f);
00577 ast_mutex_unlock(&pvt->owner->lock);
00578 }
00579 else
00580 ast_log(LOG_NOTICE, "Unable to process inband DTMF while channel is locked\n");
00581 if (f &&(f->frametype == AST_FRAME_DTMF)) {
00582 ast_log(LOG_DEBUG, "Received in-band digit %c.\n", f->subclass);
00583 }
00584 }
00585 }
00586 }
00587 return f;
00588 }
00589
00590 static struct ast_frame *oh323_read(struct ast_channel *c)
00591 {
00592 struct ast_frame *fr;
00593 struct oh323_pvt *pvt = (struct oh323_pvt *)c->tech_pvt;
00594 ast_mutex_lock(&pvt->lock);
00595 __oh323_update_info(c, pvt);
00596 fr = oh323_rtp_read(pvt);
00597 ast_mutex_unlock(&pvt->lock);
00598 return fr;
00599 }
00600
00601 static int oh323_write(struct ast_channel *c, struct ast_frame *frame)
00602 {
00603 struct oh323_pvt *pvt = (struct oh323_pvt *) c->tech_pvt;
00604 int res = 0;
00605 if (frame->frametype != AST_FRAME_VOICE) {
00606 if (frame->frametype == AST_FRAME_IMAGE) {
00607 return 0;
00608 } else {
00609 ast_log(LOG_WARNING, "Can't send %d type frames with H323 write\n", frame->frametype);
00610 return 0;
00611 }
00612 } else {
00613 if (!(frame->subclass & c->nativeformats)) {
00614 ast_log(LOG_WARNING, "Asked to transmit frame type %d, while native formats is %d (read/write = %d/%d)\n",
00615 frame->subclass, c->nativeformats, c->readformat, c->writeformat);
00616 return 0;
00617 }
00618 }
00619 if (pvt) {
00620 ast_mutex_lock(&pvt->lock);
00621 if (pvt->rtp) {
00622 res = ast_rtp_write(pvt->rtp, frame);
00623 }
00624 __oh323_update_info(c, pvt);
00625 ast_mutex_unlock(&pvt->lock);
00626 }
00627 return res;
00628 }
00629
00630 static int oh323_indicate(struct ast_channel *c, int condition)
00631 {
00632
00633 struct oh323_pvt *pvt = (struct oh323_pvt *) c->tech_pvt;
00634 char *token = (char *)NULL;
00635
00636 ast_mutex_lock(&pvt->lock);
00637 token = (pvt->cd.call_token ? strdup(pvt->cd.call_token) : NULL);
00638 ast_mutex_unlock(&pvt->lock);
00639
00640 if (h323debug)
00641 ast_log(LOG_DEBUG, "OH323: Indicating %d on %s\n", condition, token);
00642
00643 switch(condition) {
00644 case AST_CONTROL_RINGING:
00645 if (c->_state == AST_STATE_RING || c->_state == AST_STATE_RINGING) {
00646 h323_send_alerting(token);
00647 break;
00648 }
00649 if (token)
00650 free(token);
00651 return -1;
00652 case AST_CONTROL_PROGRESS:
00653 if (c->_state != AST_STATE_UP) {
00654 h323_send_progress(token);
00655 break;
00656 }
00657 if (token)
00658 free(token);
00659 return -1;
00660
00661 case AST_CONTROL_BUSY:
00662 if (c->_state != AST_STATE_UP) {
00663 h323_answering_call(token, 1);
00664 ast_mutex_lock(&pvt->lock);
00665 pvt->alreadygone = 1;
00666 ast_mutex_unlock(&pvt->lock);
00667 ast_softhangup_nolock(c, AST_SOFTHANGUP_DEV);
00668 break;
00669 }
00670 if (token)
00671 free(token);
00672 return -1;
00673 case AST_CONTROL_CONGESTION:
00674 if (c->_state != AST_STATE_UP) {
00675 h323_answering_call(token, 1);
00676 ast_mutex_lock(&pvt->lock);
00677 pvt->alreadygone = 1;
00678 ast_mutex_unlock(&pvt->lock);
00679 ast_softhangup_nolock(c, AST_SOFTHANGUP_DEV);
00680 break;
00681 }
00682 if (token)
00683 free(token);
00684 return -1;
00685 case AST_CONTROL_PROCEEDING:
00686 case -1:
00687 if (token)
00688 free(token);
00689 return -1;
00690 default:
00691 ast_log(LOG_WARNING, "Don't know how to indicate condition %d on %s\n", condition, token);
00692 if (token)
00693 free(token);
00694 return -1;
00695 }
00696
00697 if (h323debug)
00698 ast_log(LOG_DEBUG, "OH323: Indicated %d on %s\n", condition, token);
00699 if (token)
00700 free(token);
00701 oh323_update_info(c);
00702
00703 return -1;
00704 }
00705
00706 static int oh323_fixup(struct ast_channel *oldchan, struct ast_channel *newchan)
00707 {
00708 struct oh323_pvt *pvt = (struct oh323_pvt *) newchan->tech_pvt;
00709
00710 ast_mutex_lock(&pvt->lock);
00711 if (pvt->owner != oldchan) {
00712 ast_log(LOG_WARNING, "old channel wasn't %p but was %p\n", oldchan, pvt->owner);
00713 return -1;
00714 }
00715 pvt->owner = newchan;
00716 ast_mutex_unlock(&pvt->lock);
00717 return 0;
00718 }
00719
00720
00721 static struct ast_channel *__oh323_new(struct oh323_pvt *pvt, int state, const char *host)
00722 {
00723 struct ast_channel *ch;
00724 int fmt;
00725
00726
00727 ast_mutex_unlock(&pvt->lock);
00728 ch = ast_channel_alloc(1);
00729
00730 ast_mutex_lock(&usecnt_lock);
00731 usecnt++;
00732 ast_mutex_unlock(&usecnt_lock);
00733 ast_update_use_count();
00734 ast_mutex_lock(&pvt->lock);
00735 if (ch) {
00736 ch->tech = &oh323_tech;
00737 snprintf(ch->name, sizeof(ch->name), "H323/%s", host);
00738 ch->nativeformats = pvt->options.capability;
00739 if (!ch->nativeformats) {
00740 ch->nativeformats = global_options.capability;
00741 }
00742 pvt->nativeformats = ch->nativeformats;
00743 fmt = ast_best_codec(ch->nativeformats);
00744 ch->type = type;
00745 ch->fds[0] = ast_rtp_fd(pvt->rtp);
00746 if (state == AST_STATE_RING) {
00747 ch->rings = 1;
00748 }
00749 ch->writeformat = fmt;
00750 ch->rawwriteformat = fmt;
00751 ch->readformat = fmt;
00752 ch->rawreadformat = fmt;
00753
00754 if (pvt->options.dtmfmode & H323_DTMF_INBAND) {
00755 pvt->vad = ast_dsp_new();
00756 ast_dsp_set_features(pvt->vad, DSP_FEATURE_DTMF_DETECT);
00757 }
00758
00759 ch->tech_pvt = pvt;
00760
00761 pvt->owner = ch;
00762
00763 strncpy(ch->context, pvt->context, sizeof(ch->context) - 1);
00764 strncpy(ch->exten, pvt->exten, sizeof(ch->exten) - 1);
00765 ch->priority = 1;
00766 if (!ast_strlen_zero(pvt->accountcode)) {
00767 strncpy(ch->accountcode, pvt->accountcode, sizeof(ch->accountcode) - 1);
00768 }
00769 if (pvt->amaflags) {
00770 ch->amaflags = pvt->amaflags;
00771 }
00772
00773 if (!ast_strlen_zero(pvt->cid_num))
00774 ch->cid.cid_num = strdup(pvt->cid_num);
00775 else if (!ast_strlen_zero(pvt->cd.call_source_e164))
00776 ch->cid.cid_num = strdup(pvt->cd.call_source_e164);
00777 if (!ast_strlen_zero(pvt->cid_name))
00778 ch->cid.cid_name = strdup(pvt->cid_name);
00779
00780 if (!ast_strlen_zero(pvt->rdnis)) {
00781 ch->cid.cid_rdnis = strdup(pvt->rdnis);
00782 }
00783 if (!ast_strlen_zero(pvt->exten) && strcmp(pvt->exten, "s")) {
00784 ch->cid.cid_dnid = strdup(pvt->exten);
00785 }
00786 ast_setstate(ch, state);
00787 if (state != AST_STATE_DOWN) {
00788 if (ast_pbx_start(ch)) {
00789 ast_log(LOG_WARNING, "Unable to start PBX on %s\n", ch->name);
00790 ast_hangup(ch);
00791 ch = NULL;
00792 }
00793 }
00794 } else {
00795 ast_log(LOG_WARNING, "Unable to allocate channel structure\n");
00796 }
00797 return ch;
00798 }
00799
00800 static struct oh323_pvt *oh323_alloc(int callid)
00801 {
00802 struct oh323_pvt *pvt;
00803
00804 pvt = (struct oh323_pvt *) malloc(sizeof(struct oh323_pvt));
00805 if (!pvt) {
00806 ast_log(LOG_ERROR, "Couldn't allocate private structure. This is bad\n");
00807 return NULL;
00808 }
00809 memset(pvt, 0, sizeof(struct oh323_pvt));
00810 pvt->rtp = ast_rtp_new_with_bindaddr(sched, io, 1, 0,bindaddr.sin_addr);
00811 if (!pvt->rtp) {
00812 ast_log(LOG_WARNING, "Unable to create RTP session: %s\n", strerror(errno));
00813 free(pvt);
00814 return NULL;
00815 }
00816 ast_rtp_settos(pvt->rtp, tos);
00817 ast_mutex_init(&pvt->lock);
00818
00819 if ((pvt->cd).call_token == NULL) {
00820 (pvt->cd).call_token = (char *)malloc(128);
00821 }
00822 if (!pvt->cd.call_token) {
00823 ast_log(LOG_ERROR, "Not enough memory to alocate call token\n");
00824 return NULL;
00825 }
00826 memset((char *)(pvt->cd).call_token, 0, 128);
00827 pvt->cd.call_reference = callid;
00828 memcpy(&pvt->options, &global_options, sizeof(pvt->options));
00829 if (pvt->options.dtmfmode & H323_DTMF_RFC2833) {
00830 pvt->nonCodecCapability |= AST_RTP_DTMF;
00831 } else {
00832 pvt->nonCodecCapability &= ~AST_RTP_DTMF;
00833 }
00834 strncpy(pvt->context, default_context, sizeof(pvt->context) - 1);
00835 pvt->newstate = pvt->newcontrol = -1;
00836
00837 ast_mutex_lock(&iflock);
00838 pvt->next = iflist;
00839 iflist = pvt;
00840 ast_mutex_unlock(&iflock);
00841 return pvt;
00842 }
00843
00844 static struct oh323_pvt *find_call_locked(int call_reference, const char *token)
00845 {
00846 struct oh323_pvt *pvt;
00847
00848 ast_mutex_lock(&iflock);
00849 pvt = iflist;
00850 while(pvt) {
00851 if (!pvt->needdestroy && ((signed int)pvt->cd.call_reference == call_reference)) {
00852
00853 if ((token != NULL) && (!strcmp(pvt->cd.call_token, token))) {
00854 ast_mutex_lock(&pvt->lock);
00855 ast_mutex_unlock(&iflock);
00856 return pvt;
00857 } else if (token == NULL) {
00858 ast_log(LOG_WARNING, "Call Token is NULL\n");
00859 ast_mutex_lock(&pvt->lock);
00860 ast_mutex_unlock(&iflock);
00861 return pvt;
00862 }
00863 }
00864 pvt = pvt->next;
00865 }
00866 ast_mutex_unlock(&iflock);
00867 return NULL;
00868 }
00869
00870 static int update_state(struct oh323_pvt *pvt, int state, int signal)
00871 {
00872 if (!pvt)
00873 return 0;
00874 if (pvt->owner && !ast_mutex_trylock(&pvt->owner->lock)) {
00875 if (state >= 0)
00876 ast_setstate(pvt->owner, state);
00877 if (signal >= 0)
00878 ast_queue_control(pvt->owner, signal);
00879 return 1;
00880 }
00881 else {
00882 if (state >= 0)
00883 pvt->newstate = state;
00884 if (signal >= 0)
00885 pvt->newcontrol = signal;
00886 return 0;
00887 }
00888 }
00889
00890 struct oh323_user *find_user(const call_details_t *cd)
00891 {
00892 struct oh323_user *u;
00893 char iabuf[INET_ADDRSTRLEN];
00894 u = userl.users;
00895 if (userbyalias) {
00896 while(u) {
00897 if (!strcasecmp(u->name, cd->call_source_aliases)) {
00898 break;
00899 }
00900 u = u->next;
00901 }
00902 } else {
00903 while(u) {
00904 if (!strcasecmp(cd->sourceIp, ast_inet_ntoa(iabuf, sizeof(iabuf), u->addr.sin_addr))) {
00905 break;
00906 }
00907 u = u->next;
00908 }
00909 }
00910 return u;
00911 }
00912
00913 struct oh323_peer *find_peer(const char *peer, struct sockaddr_in *sin)
00914 {
00915 struct oh323_peer *p = NULL;
00916 static char iabuf[INET_ADDRSTRLEN];
00917
00918 p = peerl.peers;
00919 if (peer) {
00920 while(p) {
00921 if (!strcasecmp(p->name, peer)) {
00922 ast_log(LOG_DEBUG, "Found peer %s by name\n", peer);
00923 break;
00924 }
00925 p = p->next;
00926 }
00927 } else {
00928
00929 if (sin) {
00930 while (p) {
00931 if ((!inaddrcmp(&p->addr, sin)) ||
00932 (p->addr.sin_addr.s_addr == sin->sin_addr.s_addr)) {
00933 ast_log(LOG_DEBUG, "Found peer %s/%s by addr\n", peer, ast_inet_ntoa(iabuf, sizeof(iabuf), p->addr.sin_addr));
00934 break;
00935 }
00936 p = p->next;
00937 }
00938 }
00939 }
00940 if (!p) {
00941 ast_log(LOG_DEBUG, "Could not find peer %s by name or address\n", peer);
00942 }
00943 return p;
00944 }
00945
00946 static int create_addr(struct oh323_pvt *pvt, char *opeer)
00947 {
00948 struct hostent *hp;
00949 struct ast_hostent ahp;
00950 struct oh323_peer *p;
00951 int portno;
00952 int found = 0;
00953 char *port;
00954 char *hostn;
00955 char peer[256] = "";
00956
00957 strncpy(peer, opeer, sizeof(peer) - 1);
00958 port = strchr(peer, ':');
00959 if (port) {
00960 *port = '\0';
00961 port++;
00962 }
00963 pvt->sa.sin_family = AF_INET;
00964 ast_mutex_lock(&peerl.lock);
00965 p = find_peer(peer, NULL);
00966 if (p) {
00967 found++;
00968 memcpy(&pvt->options, &p->options, sizeof(pvt->options));
00969 if (pvt->rtp) {
00970 ast_log(LOG_DEBUG, "Setting NAT on RTP to %d\n", pvt->options.nat);
00971 ast_rtp_setnat(pvt->rtp, pvt->options.nat);
00972 }
00973 if (pvt->options.dtmfmode) {
00974 if (pvt->options.dtmfmode & H323_DTMF_RFC2833) {
00975 pvt->nonCodecCapability |= AST_RTP_DTMF;
00976 } else {
00977 pvt->nonCodecCapability &= ~AST_RTP_DTMF;
00978 }
00979 }
00980 if (p->addr.sin_addr.s_addr) {
00981 pvt->sa.sin_addr = p->addr.sin_addr;
00982 pvt->sa.sin_port = p->addr.sin_port;
00983 }
00984 }
00985 ast_mutex_unlock(&peerl.lock);
00986 if (!p && !found) {
00987 hostn = peer;
00988 if (port) {
00989 portno = atoi(port);
00990 } else {
00991 portno = h323_signalling_port;
00992 }
00993 hp = ast_gethostbyname(hostn, &ahp);
00994 if (hp) {
00995 memcpy(&pvt->options, &global_options, sizeof(pvt->options));
00996 memcpy(&pvt->sa.sin_addr, hp->h_addr, sizeof(pvt->sa.sin_addr));
00997 pvt->sa.sin_port = htons(portno);
00998 return 0;
00999 } else {
01000 ast_log(LOG_WARNING, "No such host: %s\n", peer);
01001 return -1;
01002 }
01003 } else if (!p) {
01004 return -1;
01005 } else {
01006 return 0;
01007 }
01008 }
01009 static struct ast_channel *oh323_request(const char *type, int format, void *data, int *cause)
01010 {
01011 int oldformat;
01012 struct oh323_pvt *pvt;
01013 struct ast_channel *tmpc = NULL;
01014 char *dest = (char *)data;
01015 char *ext, *host;
01016 char *h323id = NULL;
01017 char tmp[256], tmp1[256];
01018
01019 ast_log(LOG_DEBUG, "type=%s, format=%d, data=%s.\n", type, format, (char *)data);
01020 pvt = oh323_alloc(0);
01021 if (!pvt) {
01022 ast_log(LOG_WARNING, "Unable to build pvt data for '%s'\n", (char *)data);
01023 return NULL;
01024 }
01025 oldformat = format;
01026 format &= ((AST_FORMAT_MAX_AUDIO << 1) - 1);
01027 if (!format) {
01028 ast_log(LOG_NOTICE, "Asked to get a channel of unsupported format '%d'\n", format);
01029 return NULL;
01030 }
01031 strncpy(tmp, dest, sizeof(tmp) - 1);
01032 host = strchr(tmp, '@');
01033 if (host) {
01034 *host = '\0';
01035 host++;
01036 ext = tmp;
01037 } else {
01038 host = tmp;
01039 ext = NULL;
01040 }
01041 strtok_r(host, "/", &(h323id));
01042 if (!ast_strlen_zero(h323id)) {
01043 h323_set_id(h323id);
01044 }
01045 if (ext) {
01046 strncpy(pvt->exten, ext, sizeof(pvt->exten) - 1);
01047 }
01048 ast_log(LOG_DEBUG, "Extension: %s Host: %s\n", pvt->exten, host);
01049 if (!usingGk) {
01050 if (create_addr(pvt, host)) {
01051 oh323_destroy(pvt);
01052 return NULL;
01053 }
01054 }
01055 else {
01056 memcpy(&pvt->options, &global_options, sizeof(pvt->options));
01057 if (pvt->rtp) {
01058 ast_log(LOG_DEBUG, "Setting NAT on RTP to %d\n", pvt->options.nat);
01059 ast_rtp_setnat(pvt->rtp, pvt->options.nat);
01060 }
01061 if (pvt->options.dtmfmode) {
01062 if (pvt->options.dtmfmode & H323_DTMF_RFC2833) {
01063 pvt->nonCodecCapability |= AST_RTP_DTMF;
01064 } else {
01065 pvt->nonCodecCapability &= ~AST_RTP_DTMF;
01066 }
01067 }
01068 }
01069
01070 ast_mutex_lock(&caplock);
01071
01072 snprintf(tmp1, sizeof(tmp1)-1, "%s-%u", host, ++unique);
01073 tmp1[sizeof(tmp1)-1] = '\0';
01074 ast_mutex_unlock(&caplock);
01075
01076 ast_mutex_lock(&pvt->lock);
01077 tmpc = __oh323_new(pvt, AST_STATE_DOWN, tmp1);
01078 ast_mutex_unlock(&pvt->lock);
01079 if (!tmpc) {
01080 oh323_destroy(pvt);
01081 }
01082 ast_update_use_count();
01083 restart_monitor();
01084 return tmpc;
01085 }
01086
01087
01088 struct oh323_alias *find_alias(const char *source_aliases)
01089 {
01090 struct oh323_alias *a;
01091
01092 a = aliasl.aliases;
01093 while(a) {
01094 if (!strcasecmp(a->name, source_aliases)) {
01095 break;
01096 }
01097 a = a->next;
01098 }
01099 return a;
01100 }
01101
01102
01103
01104
01105
01106 int send_digit(unsigned call_reference, char digit, const char *token)
01107 {
01108 struct oh323_pvt *pvt;
01109 struct ast_frame f;
01110 int res;
01111
01112 ast_log(LOG_DEBUG, "Received Digit: %c\n", digit);
01113 pvt = find_call_locked(call_reference, token);
01114 if (!pvt) {
01115 ast_log(LOG_ERROR, "Private structure not found in send_digit.\n");
01116 return -1;
01117 }
01118 memset(&f, 0, sizeof(f));
01119 f.frametype = AST_FRAME_DTMF;
01120 f.subclass = digit;
01121 f.datalen = 0;
01122 f.samples = 800;
01123 f.offset = 0;
01124 f.data = NULL;
01125 f.mallocd = 0;
01126 f.src = "SEND_DIGIT";
01127 res = ast_queue_frame(pvt->owner, &f);
01128 ast_mutex_unlock(&pvt->lock);
01129 return res;
01130 }
01131
01132
01133
01134
01135
01136
01137 struct rtp_info *external_rtp_create(unsigned call_reference, const char * token)
01138 {
01139 struct oh323_pvt *pvt;
01140 struct sockaddr_in us;
01141 struct rtp_info *info;
01142
01143 info = (struct rtp_info *)malloc(sizeof(struct rtp_info));
01144 if (!info) {
01145 ast_log(LOG_ERROR, "Unable to allocated info structure, this is very bad\n");
01146 return NULL;
01147 }
01148 pvt = find_call_locked(call_reference, token);
01149 if (!pvt) {
01150 free(info);
01151 ast_log(LOG_ERROR, "Unable to find call %s(%d)\n", token, call_reference);
01152 return NULL;
01153 }
01154
01155 ast_rtp_get_us(pvt->rtp, &us);
01156 ast_mutex_unlock(&pvt->lock);
01157
01158 ast_inet_ntoa(info->addr, sizeof(info->addr), us.sin_addr);
01159 info->port = ntohs(us.sin_port);
01160 if (h323debug)
01161 ast_log(LOG_DEBUG, "Sending RTP 'US' %s:%d\n", info->addr, info->port);
01162 return info;
01163 }
01164
01165
01166
01167
01168 struct rtpPayloadType {
01169 int isAstFormat;
01170 int code;
01171 };
01172
01173
01174
01175
01176
01177
01178 void setup_rtp_connection(unsigned call_reference, const char *remoteIp, int remotePort, const char *token, int pt)
01179 {
01180 struct oh323_pvt *pvt;
01181 struct sockaddr_in them;
01182 struct rtpPayloadType rtptype;
01183
01184 if (h323debug)
01185 ast_log(LOG_DEBUG, "Setting up RTP connection for %s\n", token);
01186
01187
01188 pvt = find_call_locked(call_reference, token);
01189 if (!pvt) {
01190 ast_log(LOG_ERROR, "Something is wrong: rtp\n");
01191 return;
01192 }
01193 if (pvt->alreadygone) {
01194 ast_mutex_unlock(&pvt->lock);
01195 return;
01196 }
01197 rtptype = ast_rtp_lookup_pt(pvt->rtp, pt);
01198 pvt->nativeformats = rtptype.code;
01199 if (pvt->owner && !ast_mutex_trylock(&pvt->owner->lock)) {
01200 pvt->owner->nativeformats = pvt->nativeformats;
01201 ast_set_read_format(pvt->owner, pvt->owner->readformat);
01202 ast_set_write_format(pvt->owner, pvt->owner->writeformat);
01203 if (pvt->options.progress_audio)
01204 ast_queue_control(pvt->owner, AST_CONTROL_PROGRESS);
01205 ast_mutex_unlock(&pvt->owner->lock);
01206 }
01207 else {
01208 if (pvt->options.progress_audio)
01209 pvt->newcontrol = AST_CONTROL_PROGRESS;
01210 if (h323debug)
01211 ast_log(LOG_DEBUG, "RTP connection preparation for %s is pending...\n", token);
01212 }
01213
01214 them.sin_family = AF_INET;
01215
01216 them.sin_addr.s_addr = inet_addr(remoteIp);
01217 them.sin_port = htons(remotePort);
01218 ast_rtp_set_peer(pvt->rtp, &them);
01219
01220 ast_mutex_unlock(&pvt->lock);
01221
01222 if (h323debug)
01223 ast_log(LOG_DEBUG, "RTP connection prepared for %s\n", token);
01224
01225 return;
01226 }
01227
01228
01229
01230
01231
01232 void connection_made(unsigned call_reference, const char *token)
01233 {
01234 struct oh323_pvt *pvt;
01235
01236 if (h323debug)
01237 ast_log(LOG_DEBUG, "Call %s answered\n", token);
01238
01239 pvt = find_call_locked(call_reference, token);
01240 if (!pvt) {
01241 ast_log(LOG_ERROR, "Something is wrong: connection\n");
01242 return;
01243 }
01244
01245
01246 if (!pvt->outgoing) {
01247 ast_mutex_unlock(&pvt->lock);
01248 return;
01249 }
01250 if (update_state(pvt, AST_STATE_UP, AST_CONTROL_ANSWER))
01251 ast_mutex_unlock(&pvt->owner->lock);
01252 ast_mutex_unlock(&pvt->lock);
01253 return;
01254 }
01255
01256 int progress(unsigned call_reference, const char *token, int inband)
01257 {
01258 struct oh323_pvt *pvt;
01259
01260 ast_log(LOG_DEBUG, "Received ALERT/PROGRESS message for %s tones\n", (inband ? "inband" : "self-generated"));
01261
01262 pvt = find_call_locked(call_reference, token);
01263 if (!pvt) {
01264 ast_log(LOG_ERROR, "Private structure not found in progress.\n");
01265 return -1;
01266 }
01267 if (!pvt->owner) {
01268 ast_mutex_unlock(&pvt->lock);
01269 ast_log(LOG_ERROR, "No Asterisk channel associated with private structure.\n");
01270 return -1;
01271 }
01272 if (update_state(pvt, -1, (inband ? AST_CONTROL_PROGRESS : AST_CONTROL_RINGING)))
01273 ast_mutex_unlock(&pvt->owner->lock);
01274 ast_mutex_unlock(&pvt->lock);
01275
01276 return 0;
01277 }
01278
01279
01280
01281
01282
01283
01284 call_options_t *setup_incoming_call(call_details_t *cd)
01285 {
01286 struct oh323_pvt *pvt;
01287 struct oh323_user *user = NULL;
01288 struct oh323_alias *alias = NULL;
01289 char iabuf[INET_ADDRSTRLEN];
01290
01291 if (h323debug)
01292 ast_log(LOG_DEBUG, "Setting up incoming call for %s\n", cd->call_token);
01293
01294
01295 pvt = oh323_alloc(cd->call_reference);
01296
01297 if (!pvt) {
01298 ast_log(LOG_ERROR, "Unable to allocate private structure, this is bad.\n");
01299 return NULL;
01300 }
01301
01302
01303 memcpy(&pvt->cd, cd, sizeof(pvt->cd));
01304 memcpy(&pvt->options, &global_options, sizeof(pvt->options));
01305
01306 if (h323debug) {
01307 ast_verbose(VERBOSE_PREFIX_3 "Setting up Call\n");
01308 ast_verbose(VERBOSE_PREFIX_3 "\tCall token: [%s]\n", pvt->cd.call_token);
01309 ast_verbose(VERBOSE_PREFIX_3 "\tCalling party name: [%s]\n", pvt->cd.call_source_name);
01310 ast_verbose(VERBOSE_PREFIX_3 "\tCalling party number: [%s]\n", pvt->cd.call_source_e164);
01311 ast_verbose(VERBOSE_PREFIX_3 "\tCalled party name: [%s]\n", pvt->cd.call_dest_alias);
01312 ast_verbose(VERBOSE_PREFIX_3 "\tCalled party number: [%s]\n", pvt->cd.call_dest_e164);
01313 }
01314
01315
01316 if ((!strcasecmp(cd->sourceIp, gatekeeper)) && (gkroute == -1) && (usingGk)) {
01317 if (!ast_strlen_zero(cd->call_dest_e164)) {
01318 strncpy(pvt->exten, cd->call_dest_e164, sizeof(pvt->exten) - 1);
01319 strncpy(pvt->context, default_context, sizeof(pvt->context) - 1);
01320 } else {
01321 alias = find_alias(cd->call_dest_alias);
01322 if (!alias) {
01323 ast_log(LOG_ERROR, "Call for %s rejected, alias not found\n", cd->call_dest_alias);
01324 return NULL;
01325 }
01326 strncpy(pvt->exten, alias->name, sizeof(pvt->exten) - 1);
01327 strncpy(pvt->context, alias->context, sizeof(pvt->context) - 1);
01328 }
01329 } else {
01330
01331
01332 user = find_user(cd);
01333 if (!user) {
01334 if (!ast_strlen_zero(pvt->cd.call_dest_e164)) {
01335 strncpy(pvt->exten, cd->call_dest_e164, sizeof(pvt->exten) - 1);
01336 } else {
01337 strncpy(pvt->exten, cd->call_dest_alias, sizeof(pvt->exten) - 1);
01338 }
01339 if (ast_strlen_zero(default_context)) {
01340 ast_log(LOG_ERROR, "Call from '%s' rejected due to no default context\n", pvt->cd.call_source_aliases);
01341 return NULL;
01342 }
01343 strncpy(pvt->context, default_context, sizeof(pvt->context) - 1);
01344 ast_log(LOG_DEBUG, "Sending %s to context [%s]\n", cd->call_source_aliases, pvt->context);
01345
01346 #if 0
01347 memset(&pvt->options, 0, sizeof(pvt->options));
01348 #endif
01349 } else {
01350 if (user->host) {
01351 if (strcasecmp(cd->sourceIp, ast_inet_ntoa(iabuf, sizeof(iabuf), user->addr.sin_addr))) {
01352 if (ast_strlen_zero(user->context)) {
01353 if (ast_strlen_zero(default_context)) {
01354 ast_log(LOG_ERROR, "Call from '%s' rejected due to non-matching IP address (%s) and no default context\n", user->name, cd->sourceIp);
01355 return NULL;
01356 }
01357 strncpy(pvt->context, default_context, sizeof(pvt->context) - 1);
01358 } else {
01359 strncpy(pvt->context, user->context, sizeof(pvt->context) - 1);
01360 }
01361 pvt->exten[0] = 'i';
01362 pvt->exten[1] = '\0';
01363 ast_log(LOG_ERROR, "Call from '%s' rejected due to non-matching IP address (%s)s\n", user->name, cd->sourceIp);
01364 return NULL;
01365 }
01366 }
01367 strncpy(pvt->context, user->context, sizeof(pvt->context) - 1);
01368 memcpy(&pvt->options, &user->options, sizeof(pvt->options));
01369 if (!ast_strlen_zero(pvt->cd.call_dest_e164)) {
01370 strncpy(pvt->exten, cd->call_dest_e164, sizeof(pvt->exten) - 1);
01371 } else {
01372 strncpy(pvt->exten, cd->call_dest_alias, sizeof(pvt->exten) - 1);
01373 }
01374 if (!ast_strlen_zero(user->accountcode)) {
01375 strncpy(pvt->accountcode, user->accountcode, sizeof(pvt->accountcode) - 1);
01376 }
01377 if (user->amaflags) {
01378 pvt->amaflags = user->amaflags;
01379 }
01380 }
01381 }
01382 return &pvt->options;
01383 }
01384
01385
01386
01387
01388
01389
01390 static int answer_call(unsigned call_reference, const char *token)
01391 {
01392 struct oh323_pvt *pvt;
01393 struct ast_channel *c = NULL;
01394
01395 if (h323debug)
01396 ast_log(LOG_DEBUG, "Preparing Asterisk to answer for %s\n", token);
01397
01398
01399 pvt = find_call_locked(call_reference, token);
01400 if (!pvt) {
01401 ast_log(LOG_ERROR, "Something is wrong: answer_call\n");
01402 return 0;
01403 }
01404
01405 c = __oh323_new(pvt, AST_STATE_RINGING, pvt->cd.call_token);
01406
01407
01408 ast_mutex_unlock(&pvt->lock);
01409 if (!c) {
01410 ast_log(LOG_ERROR, "Couldn't create channel. This is bad\n");
01411 return 0;
01412 }
01413 return 1;
01414 }
01415
01416
01417
01418
01419
01420
01421 int setup_outgoing_call(call_details_t *cd)
01422 {
01423
01424 cleanup_call_details(cd);
01425
01426 return 1;
01427 }
01428
01429
01430
01431
01432
01433 void chan_ringing(unsigned call_reference, const char *token)
01434 {
01435 struct oh323_pvt *pvt;
01436
01437 if (h323debug)
01438 ast_log(LOG_DEBUG, "Ringing on %s\n", token);
01439
01440 pvt = find_call_locked(call_reference, token);
01441 if (!pvt) {
01442 ast_log(LOG_ERROR, "Something is wrong: ringing\n");
01443 return;
01444 }
01445 if (!pvt->owner) {
01446 ast_mutex_unlock(&pvt->lock);
01447 ast_log(LOG_ERROR, "Channel has no owner\n");
01448 return;
01449 }
01450 if (update_state(pvt, AST_STATE_RINGING, AST_CONTROL_RINGING))
01451 ast_mutex_unlock(&pvt->owner->lock);
01452 ast_mutex_unlock(&pvt->lock);
01453 return;
01454 }
01455
01456
01457
01458
01459
01460 static void cleanup_connection(unsigned call_reference, const char *call_token)
01461 {
01462 struct oh323_pvt *pvt;
01463
01464 ast_log(LOG_DEBUG, "Cleaning connection to %s\n", call_token);
01465
01466 while (1) {
01467 pvt = find_call_locked(call_reference, call_token);
01468 if (!pvt) {
01469 if (h323debug)
01470 ast_log(LOG_DEBUG, "No connection for %s\n", call_token);
01471 return;
01472 }
01473 if (!pvt->owner || !ast_mutex_trylock(&pvt->owner->lock))
01474 break;
01475 #if 1
01476 #ifdef DEBUG_THREADS
01477 ast_log(LOG_NOTICE, "Avoiding H.323 destory deadlock on %s, locked at %ld/%d by %s (%s:%d)\n", call_token, pvt->owner->lock.thread, pvt->owner->lock.reentrancy, pvt->owner->lock.func, pvt->owner->lock.file, pvt->owner->lock.lineno);
01478 #else
01479 ast_log(LOG_NOTICE, "Avoiding H.323 destory deadlock on %s\n", call_token);
01480 #endif
01481 #endif
01482 ast_mutex_unlock(&pvt->lock);
01483 usleep(1);
01484 }
01485 if (pvt->rtp) {
01486
01487 ast_rtp_destroy(pvt->rtp);
01488 pvt->rtp = NULL;
01489 }
01490
01491 if (pvt->vad) {
01492 ast_dsp_free(pvt->vad);
01493 pvt->vad = NULL;
01494 }
01495 cleanup_call_details(&pvt->cd);
01496 pvt->alreadygone = 1;
01497
01498 if (pvt->owner) {
01499 pvt->owner->_softhangup |= AST_SOFTHANGUP_DEV;
01500 ast_queue_hangup(pvt->owner);
01501 ast_mutex_unlock(&pvt->owner->lock);
01502 }
01503 ast_mutex_unlock(&pvt->lock);
01504 if (h323debug)
01505 ast_log(LOG_DEBUG, "Connection to %s cleaned\n", call_token);
01506 return;
01507 }
01508
01509 static void hangup_connection(unsigned int call_reference, const char *token, int cause)
01510 {
01511 struct oh323_pvt *pvt;
01512
01513 ast_log(LOG_DEBUG, "Hanging up connection to %s with cause %d\n", token, cause);
01514
01515 pvt = find_call_locked(call_reference, token);
01516 if (!pvt) {
01517 return;
01518 }
01519 if (pvt->owner && !ast_mutex_trylock(&pvt->owner->lock)) {
01520 pvt->owner->_softhangup |= AST_SOFTHANGUP_DEV;
01521 pvt->owner->hangupcause = pvt->hangupcause = cause;
01522 ast_queue_hangup(pvt->owner);
01523 ast_mutex_unlock(&pvt->owner->lock);
01524 }
01525 else {
01526 pvt->needhangup = 1;
01527 pvt->hangupcause = cause;
01528 ast_log(LOG_DEBUG, "Hangup for %s is pending\n", token);
01529 }
01530 ast_mutex_unlock(&pvt->lock);
01531 }
01532
01533 void set_dtmf_payload(unsigned call_reference, const char *token, int payload)
01534 {
01535 struct oh323_pvt *pvt;
01536
01537 if (h323debug)
01538 ast_log(LOG_DEBUG, "Setting DTMF payload to %d on %s\n", payload, token);
01539
01540 pvt = find_call_locked(call_reference, token);
01541 if (!pvt) {
01542 return;
01543 }
01544 if (pvt->rtp) {
01545 ast_rtp_set_rtpmap_type(pvt->rtp, payload, "audio", "telephone-event");
01546 }
01547 ast_mutex_unlock(&pvt->lock);
01548 if (h323debug)
01549 ast_log(LOG_DEBUG, "DTMF payload on %s set to %d\n", token, payload);
01550 }
01551
01552 static void set_local_capabilities(unsigned call_reference, const char *token)
01553 {
01554 struct oh323_pvt *pvt;
01555 int capability, dtmfmode;
01556
01557 if (h323debug)
01558 ast_log(LOG_DEBUG, "Setting capabilities for connection %s\n", token);
01559
01560 pvt = find_call_locked(call_reference, token);
01561 if (!pvt)
01562 return;
01563 capability = pvt->options.capability;
01564 dtmfmode = pvt->options.dtmfmode;
01565 ast_mutex_unlock(&pvt->lock);
01566 h323_set_capabilities(token, capability, dtmfmode);
01567
01568 if (h323debug)
01569 ast_log(LOG_DEBUG, "Capabilities for connection %s is set\n", token);
01570 }
01571
01572 static void *do_monitor(void *data)
01573 {
01574 int res;
01575 int reloading;
01576 struct oh323_pvt *oh323 = NULL;
01577
01578 for(;;) {
01579
01580 ast_mutex_lock(&h323_reload_lock);
01581 reloading = h323_reloading;
01582 h323_reloading = 0;
01583 ast_mutex_unlock(&h323_reload_lock);
01584 if (reloading) {
01585 if (option_verbose > 0) {
01586 ast_verbose(VERBOSE_PREFIX_1 "Reloading H.323\n");
01587 }
01588 h323_do_reload();
01589 }
01590
01591 ast_mutex_lock(&iflock);
01592 restartsearch:
01593 oh323 = iflist;
01594 while(oh323) {
01595 if (oh323->needdestroy) {
01596 __oh323_destroy(oh323);
01597 goto restartsearch;
01598 }
01599 oh323 = oh323->next;
01600 }
01601 ast_mutex_unlock(&iflock);
01602 pthread_testcancel();
01603
01604 res = ast_sched_wait(sched);
01605 if ((res < 0) || (res > 1000)) {
01606 res = 1000;
01607 }
01608 res = ast_io_wait(io, res);
01609 pthread_testcancel();
01610 ast_mutex_lock(&monlock);
01611 if (res >= 0) {
01612 ast_sched_runq(sched);
01613 }
01614 ast_mutex_unlock(&monlock);
01615 }
01616
01617 return NULL;
01618 }
01619
01620 static int restart_monitor(void)
01621 {
01622 pthread_attr_t attr;
01623
01624 if (monitor_thread == AST_PTHREADT_STOP) {
01625 return 0;
01626 }
01627 if (ast_mutex_lock(&monlock)) {
01628 ast_log(LOG_WARNING, "Unable to lock monitor\n");
01629 return -1;
01630 }
01631 if (monitor_thread == pthread_self()) {
01632 ast_mutex_unlock(&monlock);
01633 ast_log(LOG_WARNING, "Cannot kill myself\n");
01634 return -1;
01635 }
01636 if (monitor_thread && (monitor_thread != AST_PTHREADT_NULL)) {
01637
01638 pthread_kill(monitor_thread, SIGURG);
01639 } else {
01640 pthread_attr_init(&attr);
01641 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
01642
01643 if (ast_pthread_create(&monitor_thread, &attr, do_monitor, NULL) < 0) {
01644 ast_mutex_unlock(&monlock);
01645 pthread_attr_destroy(&attr);
01646 ast_log(LOG_ERROR, "Unable to start monitor thread.\n");
01647 return -1;
01648 }
01649 pthread_attr_destroy(&attr);
01650
01651 }
01652 ast_mutex_unlock(&monlock);
01653 return 0;
01654 }
01655
01656 static int h323_do_trace(int fd, int argc, char *argv[])
01657 {
01658 if (argc != 3) {
01659 return RESULT_SHOWUSAGE;
01660 }
01661 h323_debug(1, atoi(argv[2]));
01662 ast_cli(fd, "H.323 trace set to level %s\n", argv[2]);
01663 return RESULT_SUCCESS;
01664 }
01665
01666 static int h323_no_trace(int fd, int argc, char *argv[])
01667 {
01668 if (argc != 3) {
01669 return RESULT_SHOWUSAGE;
01670 }
01671 h323_debug(0,0);
01672 ast_cli(fd, "H.323 trace disabled\n");
01673 return RESULT_SUCCESS;
01674 }
01675
01676 static int h323_do_debug(int fd, int argc, char *argv[])
01677 {
01678 if (argc != 2) {
01679 return RESULT_SHOWUSAGE;
01680 }
01681 h323debug = 1;
01682 ast_cli(fd, "H323 debug enabled\n");
01683 return RESULT_SUCCESS;
01684 }
01685
01686 static int h323_no_debug(int fd, int argc, char *argv[])
01687 {
01688 if (argc != 3) {
01689 return RESULT_SHOWUSAGE;
01690 }
01691 h323debug = 0;
01692 ast_cli(fd, "H323 Debug disabled\n");
01693 return RESULT_SUCCESS;
01694 }
01695
01696 static int h323_gk_cycle(int fd, int argc, char *argv[])
01697 {
01698 #if 0
01699 if (argc != 3) {
01700 return RESULT_SHOWUSAGE;
01701 }
01702 h323_gk_urq();
01703
01704
01705 if (!gatekeeper_disable) {
01706 if (h323_set_gk(gatekeeper_discover, gatekeeper, secret)) {
01707 ast_log(LOG_ERROR, "Gatekeeper registration failed.\n");
01708 }
01709 }
01710 #endif
01711 return RESULT_SUCCESS;
01712 }
01713
01714 static int h323_ep_hangup(int fd, int argc, char *argv[])
01715 {
01716 if (argc != 3) {
01717 return RESULT_SHOWUSAGE;
01718 }
01719 if (h323_soft_hangup(argv[2])) {
01720 ast_verbose(VERBOSE_PREFIX_3 "Hangup succeeded on %s\n", argv[2]);
01721 } else {
01722 ast_verbose(VERBOSE_PREFIX_3 "Hangup failed for %s\n", argv[2]);
01723 }
01724 return RESULT_SUCCESS;
01725 }
01726
01727 static int h323_tokens_show(int fd, int argc, char *argv[])
01728 {
01729 if (argc != 3) {
01730 return RESULT_SHOWUSAGE;
01731 }
01732 h323_show_tokens();
01733 return RESULT_SUCCESS;
01734 }
01735
01736 static char trace_usage[] =
01737 "Usage: h.323 trace <level num>\n"
01738 " Enables H.323 stack tracing for debugging purposes\n";
01739
01740 static char no_trace_usage[] =
01741 "Usage: h.323 no trace\n"
01742 " Disables H.323 stack tracing for debugging purposes\n";
01743
01744 static char debug_usage[] =
01745 "Usage: h.323 debug\n"
01746 " Enables H.323 debug output\n";
01747
01748 static char no_debug_usage[] =
01749 "Usage: h.323 no debug\n"
01750 " Disables H.323 debug output\n";
01751
01752 static char show_codec_usage[] =
01753 "Usage: h.323 show codec\n"
01754 " Shows all enabled codecs\n";
01755
01756 static char show_cycle_usage[] =
01757 "Usage: h.323 gk cycle\n"
01758 " Manually re-register with the Gatekeper (Currently Disabled)\n";
01759
01760 static char show_hangup_usage[] =
01761 "Usage: h.323 hangup <token>\n"
01762 " Manually try to hang up call identified by <token>\n";
01763
01764 static char show_tokens_usage[] =
01765 "Usage: h.323 show tokens\n"
01766 " Print out all active call tokens\n";
01767
01768 static char h323_reload_usage[] =
01769 "Usage: h323 reload\n"
01770 " Reloads H.323 configuration from sip.conf\n";
01771
01772 static struct ast_cli_entry cli_trace =
01773 { { "h.323", "trace", NULL }, h323_do_trace, "Enable H.323 Stack Tracing", trace_usage };
01774 static struct ast_cli_entry cli_no_trace =
01775 { { "h.323", "no", "trace", NULL }, h323_no_trace, "Disable H.323 Stack Tracing", no_trace_usage };
01776 static struct ast_cli_entry cli_debug =
01777 { { "h.323", "debug", NULL }, h323_do_debug, "Enable H.323 debug", debug_usage };
01778 static struct ast_cli_entry cli_no_debug =
01779 { { "h.323", "no", "debug", NULL }, h323_no_debug, "Disable H.323 debug", no_debug_usage };
01780 static struct ast_cli_entry cli_show_codecs =
01781 { { "h.323", "show", "codecs", NULL }, h323_show_codec, "Show enabled codecs", show_codec_usage };
01782 static struct ast_cli_entry cli_gk_cycle =
01783 { { "h.323", "gk", "cycle", NULL }, h323_gk_cycle, "Manually re-register with the Gatekeper", show_cycle_usage };
01784 static struct ast_cli_entry cli_hangup_call =
01785 { { "h.323", "hangup", NULL }, h323_ep_hangup, "Manually try to hang up a call", show_hangup_usage };
01786 static struct ast_cli_entry cli_show_tokens =
01787 { { "h.323", "show", "tokens", NULL }, h323_tokens_show, "Show all active call tokens", show_tokens_usage };
01788
01789 static int update_common_options(struct ast_variable *v, struct call_options *options)
01790 {
01791 unsigned int format;
01792 int tmp;
01793
01794 if (!strcasecmp(v->name, "allow")) {
01795 format = ast_getformatbyname(v->value);
01796 if (format < 1)
01797 ast_log(LOG_WARNING, "Cannot allow unknown format '%s'\n", v->value);
01798 else
01799 options->capability |= format;
01800 } else if (!strcasecmp(v->name, "disallow")) {
01801 format = ast_getformatbyname(v->value);
01802 if (format < 1)
01803 ast_log(LOG_WARNING, "Cannot disallow unknown format '%s'\n", v->value);
01804 else
01805 options->capability &= ~format;
01806 } else if (!strcasecmp(v->name, "dtmfmode")) {
01807 if (!strcasecmp(v->value, "inband")) {
01808 options->dtmfmode = H323_DTMF_INBAND;
01809 } else if (!strcasecmp(v->value, "rfc2833")) {
01810 options->dtmfmode = H323_DTMF_RFC2833;
01811 } else {
01812 ast_log(LOG_WARNING, "Unknown dtmf mode '%s', using rfc2833\n", v->value);
01813 options->dtmfmode = H323_DTMF_RFC2833;
01814 }
01815 } else if (!strcasecmp(v->name, "dtmfcodec")) {
01816 tmp = atoi(v->value);
01817 if (tmp < 96)
01818 ast_log(LOG_WARNING, "Invalid global dtmfcodec value %s\n", v->value);
01819 else
01820 options->dtmfcodec = tmp;
01821 } else if (!strcasecmp(v->name, "bridge")) {
01822 options->bridge = ast_true(v->value);
01823 } else if (!strcasecmp(v->name, "nat")) {
01824 options->nat = ast_true(v->value);
01825 } else if (!strcasecmp(v->name, "noFastStart")) {
01826 options->noFastStart = ast_true(v->value);
01827 } else if (!strcasecmp(v->name, "noH245Tunneling")) {
01828 options->noH245Tunneling = ast_true(v->value);
01829 } else if (!strcasecmp(v->name, "noSilenceSuppression")) {
01830 options->noSilenceSuppression = ast_true(v->value);
01831 } else if (!strcasecmp(v->name, "progress_setup")) {
01832 tmp = atoi(v->value);
01833 if ((tmp != 0) && (tmp != 1) && (tmp != 3) && (tmp != 8)) {
01834 ast_log(LOG_WARNING, "Invalid value %d for progress_setup at line %d, assuming 0\n", tmp, v->lineno);
01835 tmp = 0;
01836 }
01837 options->progress_setup = tmp;
01838 } else if (!strcasecmp(v->name, "progress_alert")) {
01839 tmp = atoi(v->value);
01840 if ((tmp != 0) && (tmp != 8)) {
01841 ast_log(LOG_WARNING, "Invalud value %d for progress_alert at line %d, assuming 0\n", tmp, v->lineno);
01842 tmp = 0;
01843 }
01844 options->progress_alert = tmp;
01845 } else if (!strcasecmp(v->name, "progress_audio")) {
01846 options->progress_audio = ast_true(v->value);
01847 } else
01848 return 1;
01849
01850 return 0;
01851 }
01852
01853 static struct oh323_alias *build_alias(char *name, struct ast_variable *v)
01854 {
01855 struct oh323_alias *alias;
01856
01857 alias = (struct oh323_alias *)malloc(sizeof(struct oh323_alias));
01858 if (alias) {
01859 memset(alias, 0, sizeof(struct oh323_alias));
01860 strncpy(alias->name, name, sizeof(alias->name) - 1);
01861 while (v) {
01862 if (!strcasecmp(v->name, "e164")) {
01863 strncpy(alias->e164, v->value, sizeof(alias->e164) - 1);
01864 } else if (!strcasecmp(v->name, "prefix")) {
01865 strncpy(alias->prefix, v->value, sizeof(alias->prefix) - 1);
01866 } else if (!strcasecmp(v->name, "context")) {
01867 strncpy(alias->context, v->value, sizeof(alias->context) - 1);
01868 } else if (!strcasecmp(v->name, "secret")) {
01869 strncpy(alias->secret, v->value, sizeof(alias->secret) - 1);
01870 } else {
01871 if (strcasecmp(v->value, "h323")) {
01872 ast_log(LOG_WARNING, "Keyword %s does not make sense in type=h323\n", v->value);
01873 }
01874 }
01875 v = v->next;
01876 }
01877 }
01878 return alias;
01879 }
01880
01881 static struct oh323_user *build_user(char *name, struct ast_variable *v)
01882 {
01883 struct oh323_user *user;
01884 int format;
01885
01886 user = (struct oh323_user *)malloc(sizeof(struct oh323_user));
01887 if (user) {
01888 memset(user, 0, sizeof(struct oh323_user));
01889 strncpy(user->name, name, sizeof(user->name) - 1);
01890 memcpy(&user->options, &global_options, sizeof(user->options));
01891
01892 strncpy(user->context, default_context, sizeof(user->context) - 1);
01893 while(v) {
01894 if (!strcasecmp(v->name, "context")) {
01895 strncpy(user->context, v->value, sizeof(user->context) - 1);
01896 } else if (!update_common_options(v, &user->options)) {
01897
01898 } else if (!strcasecmp(v->name, "secret")) {
01899 strncpy(user->secret, v->value, sizeof(user->secret) - 1);
01900 } else if (!strcasecmp(v->name, "callerid")) {
01901 strncpy(user->callerid, v->value, sizeof(user->callerid) - 1);
01902 } else if (!strcasecmp(v->name, "accountcode")) {
01903 strncpy(user->accountcode, v->value, sizeof(user->accountcode) - 1);
01904 } else if (!strcasecmp(v->name, "host")) {
01905 if (!strcasecmp(v->value, "dynamic")) {
01906 ast_log(LOG_ERROR, "A dynamic host on a type=user does not make any sense\n");
01907 free(user);
01908 return NULL;
01909 } else if (ast_get_ip(&user->addr, v->value)) {
01910 free(user);
01911 return NULL;
01912 }
01913
01914 user->host = 1;
01915 } else if (!strcasecmp(v->name, "amaflags")) {
01916 format = ast_cdr_amaflags2int(v->value);
01917 if (format < 0) {
01918 ast_log(LOG_WARNING, "Invalid AMA Flags: %s at line %d\n", v->value, v->lineno);
01919 } else {
01920 user->amaflags = format;
01921 }
01922 }
01923 v = v->next;
01924 }
01925 }
01926 return user;
01927 }
01928
01929 static struct oh323_peer *build_peer(char *name, struct ast_variable *v)
01930 {
01931 struct oh323_peer *peer;
01932 struct oh323_peer *prev;
01933 struct ast_ha *oldha = NULL;
01934 int found=0;
01935
01936 prev = NULL;
01937 ast_mutex_lock(&peerl.lock);
01938 peer = peerl.peers;
01939
01940 while(peer) {
01941 if (!strcasecmp(peer->name, name)) {
01942 break;
01943 }
01944 prev = peer;
01945 peer = peer->next;
01946 }
01947
01948 if (peer) {
01949 found++;
01950
01951 if (prev) {
01952 prev->next = peer->next;
01953 } else {
01954 peerl.peers = peer->next;
01955 }
01956 ast_mutex_unlock(&peerl.lock);
01957 } else {
01958 ast_mutex_unlock(&peerl.lock);
01959 peer = (struct oh323_peer*)malloc(sizeof(struct oh323_peer));
01960 if (peer)
01961 memset(peer, 0, sizeof(struct oh323_peer));
01962 }
01963 if (peer) {
01964 if (!found) {
01965 strncpy(peer->name, name, sizeof(peer->name) - 1);
01966 peer->addr.sin_port = htons(h323_signalling_port);
01967 peer->addr.sin_family = AF_INET;
01968 }
01969 oldha = peer->ha;
01970 peer->ha = NULL;
01971 peer->addr.sin_family = AF_INET;
01972 memcpy(&peer->options, &global_options, sizeof(peer->options));
01973
01974 while(v) {
01975 if (!update_common_options(v, &peer->options)) {
01976
01977 } else if (!strcasecmp(v->name, "host")) {
01978 if (!strcasecmp(v->value, "dynamic")) {
01979 ast_log(LOG_ERROR, "Dynamic host configuration not implemented.\n");
01980 free(peer);
01981 return NULL;
01982 }
01983 if (ast_get_ip(&peer->addr, v->value)) {
01984 ast_log(LOG_ERROR, "Could not determine IP for %s\n", v->value);
01985 free(peer);
01986 return NULL;
01987 }
01988 } else if (!strcasecmp(v->name, "port")) {
01989 peer->addr.sin_port = htons(atoi(v->value));
01990 }
01991 v=v->next;
01992 }
01993 }
01994 return peer;
01995 }
01996
01997 int reload_config(void)
01998 {
01999 int format;
02000 struct ast_config *cfg;
02001 struct ast_variable *v;
02002 struct oh323_peer *peer = NULL;
02003 struct oh323_user *user = NULL;
02004 struct oh323_alias *alias = NULL;
02005 struct ast_hostent ahp; struct hostent *hp;
02006 char *cat;
02007 char *utype;
02008
02009 cfg = ast_config_load(config);
02010
02011
02012 if (!cfg) {
02013 ast_log(LOG_NOTICE, "Unable to load config %s, H.323 disabled\n", config);
02014 return 1;
02015 }
02016
02017
02018 if (!h323_end_point_exist()) {
02019 h323_end_point_create();
02020 }
02021 h323debug = 0;
02022 memset(&bindaddr, 0, sizeof(bindaddr));
02023 memset(&global_options, 0, sizeof(global_options));
02024 global_options.dtmfcodec = 101;
02025 global_options.dtmfmode = H323_DTMF_RFC2833;
02026 global_options.capability = AST_FORMAT_G723_1 | AST_FORMAT_GSM | AST_FORMAT_ULAW | AST_FORMAT_ALAW | AST_FORMAT_G729A | AST_FORMAT_H261;
02027 global_options.bridge = 1;
02028 v = ast_variable_browse(cfg, "general");
02029 while(v) {
02030
02031 if (!strcasecmp(v->name, "port")) {
02032 h323_signalling_port = (int)strtol(v->value, NULL, 10);
02033 } else if (!strcasecmp(v->name, "bindaddr")) {
02034 if (!(hp = ast_gethostbyname(v->value, &ahp))) {
02035 ast_log(LOG_WARNING, "Invalid address: %s\n", v->value);
02036 } else {
02037 memcpy(&bindaddr.sin_addr, hp->h_addr, sizeof(bindaddr.sin_addr));
02038 }
02039 } else if (!strcasecmp(v->name, "tos")) {
02040 if (sscanf(v->value, "%30d", &format)) {
02041 tos = format & 0xff;
02042 } else if (!strcasecmp(v->value, "lowdelay")) {
02043 tos = IPTOS_LOWDELAY;
02044 } else if (!strcasecmp(v->value, "throughput")) {
02045 tos = IPTOS_THROUGHPUT;
02046 } else if (!strcasecmp(v->value, "reliability")) {
02047 tos = IPTOS_RELIABILITY;
02048 } else if (!strcasecmp(v->value, "mincost")) {
02049 tos = IPTOS_MINCOST;
02050 } else if (!strcasecmp(v->value, "none")) {
02051 tos = 0;
02052 } else {
02053 ast_log(LOG_WARNING, "Invalid tos value at line %d, should be 'lowdelay', 'throughput', 'reliability', 'mincost', or 'none'\n", v->lineno);
02054 }
02055 } else if (!strcasecmp(v->name, "gatekeeper")) {
02056 if (!strcasecmp(v->value, "DISABLE")) {
02057 gatekeeper_disable = 1;
02058 usingGk = 0;
02059 } else if (!strcasecmp(v->value, "DISCOVER")) {
02060 gatekeeper_disable = 0;
02061 gatekeeper_discover = 1;
02062 usingGk = 1;
02063 } else {
02064 gatekeeper_disable = 0;
02065 usingGk = 1;
02066 strncpy(gatekeeper, v->value, sizeof(gatekeeper) - 1);
02067 }
02068 } else if (!strcasecmp(v->name, "secret")) {
02069 strncpy(secret, v->value, sizeof(secret) - 1);
02070 } else if (!strcasecmp(v->name, "AllowGKRouted")) {
02071 gkroute = ast_true(v->value);
02072 } else if (!strcasecmp(v->name, "context")) {
02073 strncpy(default_context, v->value, sizeof(default_context) - 1);
02074 ast_verbose(VERBOSE_PREFIX_2 "Setting default context to %s\n", default_context);
02075 } else if (!strcasecmp(v->name, "UserByAlias")) {
02076 userbyalias = ast_true(v->value);
02077 } else if (!update_common_options(v, &global_options)) {
02078
02079 }
02080 v = v->next;
02081 }
02082
02083 cat = ast_category_browse(cfg, NULL);
02084 while(cat) {
02085 if (strcasecmp(cat, "general")) {
02086 utype = ast_variable_retrieve(cfg, cat, "type");
02087 if (utype) {
02088 if (!strcasecmp(utype, "user")) {
02089 user = build_user(cat, ast_variable_browse(cfg, cat));
02090 if (user) {
02091 ast_mutex_lock(&userl.lock);
02092 user->next = userl.users;
02093 userl.users = user;
02094 ast_mutex_unlock(&userl.lock);
02095 }
02096 } else if (!strcasecmp(utype, "peer")) {
02097 peer = build_peer(cat, ast_variable_browse(cfg, cat));
02098 if (peer) {
02099 ast_mutex_lock(&peerl.lock);
02100 peer->next = peerl.peers;
02101 peerl.peers = peer;
02102 ast_mutex_unlock(&peerl.lock);
02103 }
02104 } else if (!strcasecmp(utype, "friend")) {
02105 user = build_user(cat, ast_variable_browse(cfg, cat));
02106 peer = build_peer(cat, ast_variable_browse(cfg, cat));
02107 if (user) {
02108 ast_mutex_lock(&userl.lock);
02109 user->next = userl.users;
02110 userl.users = user;
02111 ast_mutex_unlock(&userl.lock);
02112 }
02113 if (peer) {
02114 ast_mutex_lock(&peerl.lock);
02115 peer->next = peerl.peers;
02116 peerl.peers = peer;
02117 ast_mutex_unlock(&peerl.lock);
02118 }
02119 } else if (!strcasecmp(utype, "h323") || !strcasecmp(utype, "alias")) {
02120 alias = build_alias(cat, ast_variable_browse(cfg, cat));
02121 if (alias) {
02122 ast_mutex_lock(&aliasl.lock);
02123 alias->next = aliasl.aliases;
02124 aliasl.aliases = alias;
02125 ast_mutex_unlock(&aliasl.lock);
02126 }
02127 } else {
02128 ast_log(LOG_WARNING, "Unknown type '%s' for '%s' in %s\n", utype, cat, config);
02129 }
02130 } else {
02131 ast_log(LOG_WARNING, "Section '%s' lacks type\n", cat);
02132 }
02133 }
02134 cat = ast_category_browse(cfg, cat);
02135 }
02136 ast_config_destroy(cfg);
02137
02138
02139 while (alias) {
02140 if (h323_set_alias(alias)) {
02141 ast_log(LOG_ERROR, "Alias %s rejected by endpoint\n", alias->name);
02142 return -1;
02143 }
02144 alias = alias->next;
02145 }
02146
02147 return 0;
02148 }
02149
02150 void delete_users(void)
02151 {
02152 struct oh323_user *user, *userlast;
02153 struct oh323_peer *peer;
02154
02155
02156 ast_mutex_lock(&userl.lock);
02157 for (user=userl.users;user;) {
02158 userlast = user;
02159 user=user->next;
02160 free(userlast);
02161 }
02162 userl.users=NULL;
02163 ast_mutex_unlock(&userl.lock);
02164 ast_mutex_lock(&peerl.lock);
02165 for (peer=peerl.peers;peer;) {
02166
02167 peer->delme = 1;
02168 peer = peer->next;
02169 }
02170 ast_mutex_unlock(&peerl.lock);
02171 }
02172
02173 void delete_aliases(void)
02174 {
02175 struct oh323_alias *alias, *aliaslast;
02176
02177
02178 ast_mutex_lock(&aliasl.lock);
02179 for (alias=aliasl.aliases;alias;) {
02180 aliaslast = alias;
02181 alias=alias->next;
02182 free(aliaslast);
02183 }
02184 aliasl.aliases=NULL;
02185 ast_mutex_unlock(&aliasl.lock);
02186 }
02187
02188 void prune_peers(void)
02189 {
02190
02191 struct oh323_peer *peer, *peerlast, *peernext;
02192 ast_mutex_lock(&peerl.lock);
02193 peerlast = NULL;
02194 for (peer=peerl.peers;peer;) {
02195 peernext = peer->next;
02196 if (peer->delme) {
02197 free(peer);
02198 if (peerlast) {
02199 peerlast->next = peernext;
02200 } else {
02201 peerl.peers = peernext;
02202 }
02203 } else {
02204 peerlast = peer;
02205 }
02206 peer = peernext;
02207 }
02208 ast_mutex_unlock(&peerl.lock);
02209 }
02210
02211 static int h323_reload(int fd, int argc, char *argv[])
02212 {
02213 ast_mutex_lock(&h323_reload_lock);
02214 if (h323_reloading) {
02215 ast_verbose("Previous H.323 reload not yet done\n");
02216 } else {
02217 h323_reloading = 1;
02218 }
02219 ast_mutex_unlock(&h323_reload_lock);
02220 restart_monitor();
02221 return 0;
02222 }
02223
02224 static int h323_do_reload(void)
02225 {
02226 delete_users();
02227 delete_aliases();
02228 prune_peers();
02229 reload_config();
02230 restart_monitor();
02231 return 0;
02232 }
02233
02234 int reload(void)
02235 {
02236 return h323_reload(0, 0, NULL);
02237 }
02238
02239 static struct ast_cli_entry cli_h323_reload =
02240 { { "h.323", "reload", NULL }, h323_reload, "Reload H.323 configuration", h323_reload_usage };
02241
02242 static struct ast_rtp *oh323_get_rtp_peer(struct ast_channel *chan)
02243 {
02244 struct oh323_pvt *pvt;
02245 pvt = (struct oh323_pvt *) chan->tech_pvt;
02246 if (pvt && pvt->rtp && pvt->options.bridge) {
02247 return pvt->rtp;
02248 }
02249 return NULL;
02250 }
02251
02252 static struct ast_rtp *oh323_get_vrtp_peer(struct ast_channel *chan)
02253 {
02254 return NULL;
02255 }
02256
02257 static char *convertcap(int cap)
02258 {
02259 switch (cap) {
02260 case AST_FORMAT_G723_1:
02261 return "G.723";
02262 case AST_FORMAT_GSM:
02263 return "GSM";
02264 case AST_FORMAT_ULAW:
02265 return "ULAW";
02266 case AST_FORMAT_ALAW:
02267 return "ALAW";
02268 case AST_FORMAT_ADPCM:
02269 return "G.728";
02270 case AST_FORMAT_G729A:
02271 return "G.729";
02272 case AST_FORMAT_SPEEX:
02273 return "SPEEX";
02274 case AST_FORMAT_ILBC:
02275 return "ILBC";
02276 default:
02277 ast_log(LOG_NOTICE, "Don't know how to deal with mode %d\n", cap);
02278 return NULL;
02279 }
02280 }
02281
02282 static int oh323_set_rtp_peer(struct ast_channel *chan, struct ast_rtp *rtp, struct ast_rtp *vrtp, int codecs, int nat_active)
02283 {
02284
02285 struct oh323_pvt *pvt;
02286 struct sockaddr_in them;
02287 struct sockaddr_in us;
02288 char *mode;
02289 char iabuf[INET_ADDRSTRLEN];
02290
02291 if (!rtp) {
02292 return 0;
02293 }
02294
02295 mode = convertcap(chan->writeformat);
02296 pvt = (struct oh323_pvt *) chan->tech_pvt;
02297 if (!pvt) {
02298 ast_log(LOG_ERROR, "No Private Structure, this is bad\n");
02299 return -1;
02300 }
02301 ast_rtp_get_peer(rtp, &them);
02302 ast_rtp_get_us(rtp, &us);
02303 h323_native_bridge(pvt->cd.call_token, ast_inet_ntoa(iabuf, sizeof(iabuf), them.sin_addr), mode);
02304 return 0;
02305 }
02306
02307 static struct ast_rtp_protocol oh323_rtp = {
02308 .type = type,
02309 .get_rtp_info = oh323_get_rtp_peer,
02310 .get_vrtp_info = oh323_get_vrtp_peer,
02311 .set_rtp_peer = oh323_set_rtp_peer,
02312 };
02313
02314 int load_module()
02315 {
02316 int res;
02317 ast_mutex_init(&userl.lock);
02318 ast_mutex_init(&peerl.lock);
02319 ast_mutex_init(&aliasl.lock);
02320 sched = sched_context_create();
02321 if (!sched) {
02322 ast_log(LOG_WARNING, "Unable to create schedule context\n");
02323 }
02324 io = io_context_create();
02325 if (!io) {
02326 ast_log(LOG_WARNING, "Unable to create I/O context\n");
02327 }
02328 res = reload_config();
02329 if (res) {
02330 return 0;
02331 } else {
02332
02333 if (ast_channel_register(&oh323_tech)) {
02334 ast_log(LOG_ERROR, "Unable to register channel class %s\n", type);
02335 h323_end_process();
02336 return -1;
02337 }
02338 ast_cli_register(&cli_debug);
02339 ast_cli_register(&cli_no_debug);
02340 ast_cli_register(&cli_trace);
02341 ast_cli_register(&cli_no_trace);
02342 ast_cli_register(&cli_show_codecs);
02343 ast_cli_register(&cli_gk_cycle);
02344 ast_cli_register(&cli_hangup_call);
02345 ast_cli_register(&cli_show_tokens);
02346 ast_cli_register(&cli_h323_reload);
02347
02348 ast_rtp_proto_register(&oh323_rtp);
02349
02350
02351 h323_callback_register(setup_incoming_call,
02352 setup_outgoing_call,
02353 external_rtp_create,
02354 setup_rtp_connection,
02355 cleanup_connection,
02356 chan_ringing,
02357 connection_made,
02358 send_digit,
02359 answer_call,
02360 progress,
02361 set_dtmf_payload,
02362 hangup_connection,
02363 set_local_capabilities);
02364
02365 if (h323_start_listener(h323_signalling_port, bindaddr)) {
02366 ast_log(LOG_ERROR, "Unable to create H323 listener.\n");
02367 return -1;
02368 }
02369
02370 if (!gatekeeper_disable) {
02371 if (h323_set_gk(gatekeeper_discover, gatekeeper, secret)) {
02372 ast_log(LOG_ERROR, "Gatekeeper registration failed.\n");
02373 return 0;
02374 }
02375 }
02376
02377 restart_monitor();
02378 }
02379 return res;
02380 }
02381
02382 int unload_module()
02383 {
02384 struct oh323_pvt *p, *pl;
02385
02386
02387 ast_cli_unregister(&cli_debug);
02388 ast_cli_unregister(&cli_no_debug);
02389 ast_cli_unregister(&cli_trace);
02390 ast_cli_unregister(&cli_no_trace);
02391 ast_cli_unregister(&cli_show_codecs);
02392 ast_cli_unregister(&cli_gk_cycle);
02393 ast_cli_unregister(&cli_hangup_call);
02394 ast_cli_unregister(&cli_show_tokens);
02395 ast_cli_unregister(&cli_h323_reload);
02396 ast_rtp_proto_unregister(&oh323_rtp);
02397 ast_channel_unregister(&oh323_tech);
02398
02399 if (!ast_mutex_lock(&iflock)) {
02400
02401 p = iflist;
02402 while(p) {
02403 if (p->owner) {
02404 ast_softhangup(p->owner, AST_SOFTHANGUP_APPUNLOAD);
02405 }
02406 p = p->next;
02407 }
02408 iflist = NULL;
02409 ast_mutex_unlock(&iflock);
02410 } else {
02411 ast_log(LOG_WARNING, "Unable to lock the interface list\n");
02412 return -1;
02413 }
02414 if (!ast_mutex_lock(&monlock)) {
02415 if (monitor_thread && (monitor_thread != AST_PTHREADT_STOP)) {
02416
02417 pthread_cancel(monitor_thread);
02418 pthread_kill(monitor_thread, SIGURG);
02419 pthread_join(monitor_thread, NULL);
02420 }
02421 monitor_thread = AST_PTHREADT_STOP;
02422 ast_mutex_unlock(&monlock);
02423 } else {
02424 ast_log(LOG_WARNING, "Unable to lock the monitor\n");
02425 return -1;
02426 }
02427 if (!ast_mutex_lock(&iflock)) {
02428
02429 p = iflist;
02430 while(p) {
02431 pl = p;
02432 p = p->next;
02433
02434 ast_mutex_destroy(&pl->lock);
02435 free(pl);
02436 }
02437 iflist = NULL;
02438 ast_mutex_unlock(&iflock);
02439 } else {
02440 ast_log(LOG_WARNING, "Unable to lock the interface list\n");
02441 return -1;
02442 }
02443 h323_gk_urq();
02444 h323_end_process();
02445 io_context_destroy(io);
02446 sched_context_destroy(sched);
02447 delete_users();
02448 delete_aliases();
02449 prune_peers();
02450 ast_mutex_destroy(&aliasl.lock);
02451 ast_mutex_destroy(&userl.lock);
02452 ast_mutex_destroy(&peerl.lock);
02453 return 0;
02454 }
02455
02456 int usecount()
02457 {
02458 return usecnt;
02459 }
02460
02461 char *description()
02462 {
02463 return (char *) desc;
02464 }
02465
02466 char *key()
02467 {
02468 return ASTERISK_GPL_KEY;
02469 }