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 #include "asterisk.h"
00031
00032 #ifdef HAVE_PRI
00033
00034 #include <errno.h>
00035 #include <ctype.h>
00036 #include <signal.h>
00037
00038 #include "asterisk/utils.h"
00039 #include "asterisk/options.h"
00040 #include "asterisk/pbx.h"
00041 #include "asterisk/app.h"
00042 #include "asterisk/file.h"
00043 #include "asterisk/callerid.h"
00044 #include "asterisk/say.h"
00045 #include "asterisk/manager.h"
00046 #include "asterisk/astdb.h"
00047 #include "asterisk/causes.h"
00048 #include "asterisk/musiconhold.h"
00049 #include "asterisk/cli.h"
00050 #include "asterisk/transcap.h"
00051 #include "asterisk/features.h"
00052 #include "asterisk/aoc.h"
00053
00054 #include "sig_pri.h"
00055 #ifndef PRI_EVENT_FACILITY
00056 #error "Upgrade your libpri"
00057 #endif
00058
00059
00060 #undef SUPPORT_USERUSER
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075 #define FORCE_RESTART_UNAVAIL_CHANS 1
00076
00077 #if defined(HAVE_PRI_CCSS)
00078 struct sig_pri_cc_agent_prv {
00079
00080 struct sig_pri_span *pri;
00081
00082 long cc_id;
00083
00084 unsigned char cc_request_response_pending;
00085 };
00086
00087 struct sig_pri_cc_monitor_instance {
00088
00089 struct sig_pri_span *pri;
00090
00091 long cc_id;
00092
00093 int core_id;
00094
00095 char name[1];
00096 };
00097
00098
00099 static const char *sig_pri_cc_type_name;
00100
00101 static struct ao2_container *sig_pri_cc_monitors;
00102 #endif
00103
00104 static int pri_matchdigittimeout = 3000;
00105
00106 static int pri_gendigittimeout = 8000;
00107
00108 #define DCHAN_NOTINALARM (1 << 0)
00109 #define DCHAN_UP (1 << 1)
00110
00111
00112 #define PRI_CHANNEL(p) ((p) & 0xff)
00113 #define PRI_SPAN(p) (((p) >> 8) & 0xff)
00114 #define PRI_EXPLICIT (1 << 16)
00115 #define PRI_CIS_CALL (1 << 17)
00116 #define PRI_HELD_CALL (1 << 18)
00117
00118
00119 #define DCHAN_AVAILABLE (DCHAN_NOTINALARM | DCHAN_UP)
00120
00121 static int pri_active_dchan_index(struct sig_pri_span *pri);
00122
00123 static const char *sig_pri_call_level2str(enum sig_pri_call_level level)
00124 {
00125 switch (level) {
00126 case SIG_PRI_CALL_LEVEL_IDLE:
00127 return "Idle";
00128 case SIG_PRI_CALL_LEVEL_SETUP:
00129 return "Setup";
00130 case SIG_PRI_CALL_LEVEL_OVERLAP:
00131 return "Overlap";
00132 case SIG_PRI_CALL_LEVEL_PROCEEDING:
00133 return "Proceeding";
00134 case SIG_PRI_CALL_LEVEL_ALERTING:
00135 return "Alerting";
00136 case SIG_PRI_CALL_LEVEL_DEFER_DIAL:
00137 return "DeferDial";
00138 case SIG_PRI_CALL_LEVEL_CONNECT:
00139 return "Connect";
00140 }
00141 return "Unknown";
00142 }
00143
00144 static inline void pri_rel(struct sig_pri_span *pri)
00145 {
00146 ast_mutex_unlock(&pri->lock);
00147 }
00148
00149 static unsigned int PVT_TO_CHANNEL(struct sig_pri_chan *p)
00150 {
00151 int res = (((p)->prioffset) | ((p)->logicalspan << 8) | (p->mastertrunkgroup ? PRI_EXPLICIT : 0));
00152 ast_debug(5, "prioffset: %d mastertrunkgroup: %d logicalspan: %d result: %d\n",
00153 p->prioffset, p->mastertrunkgroup, p->logicalspan, res);
00154
00155 return res;
00156 }
00157
00158 static void sig_pri_handle_dchan_exception(struct sig_pri_span *pri, int index)
00159 {
00160 if (pri->calls->handle_dchan_exception)
00161 pri->calls->handle_dchan_exception(pri, index);
00162 }
00163
00164 static void sig_pri_set_dialing(struct sig_pri_chan *p, int is_dialing)
00165 {
00166 if (p->calls->set_dialing) {
00167 p->calls->set_dialing(p->chan_pvt, is_dialing);
00168 }
00169 }
00170
00171 static void sig_pri_set_digital(struct sig_pri_chan *p, int is_digital)
00172 {
00173 p->digital = is_digital;
00174 if (p->calls->set_digital) {
00175 p->calls->set_digital(p->chan_pvt, is_digital);
00176 }
00177 }
00178
00179 static void sig_pri_set_outgoing(struct sig_pri_chan *p, int is_outgoing)
00180 {
00181 p->outgoing = is_outgoing;
00182 if (p->calls->set_outgoing) {
00183 p->calls->set_outgoing(p->chan_pvt, is_outgoing);
00184 }
00185 }
00186
00187 void sig_pri_set_alarm(struct sig_pri_chan *p, int in_alarm)
00188 {
00189 if (sig_pri_is_alarm_ignored(p->pri)) {
00190
00191 in_alarm = 0;
00192 }
00193
00194
00195
00196
00197
00198
00199 p->resetting = SIG_PRI_RESET_IDLE;
00200
00201 p->inalarm = in_alarm;
00202 if (p->calls->set_alarm) {
00203 p->calls->set_alarm(p->chan_pvt, in_alarm);
00204 }
00205 }
00206
00207 static const char *sig_pri_get_orig_dialstring(struct sig_pri_chan *p)
00208 {
00209 if (p->calls->get_orig_dialstring) {
00210 return p->calls->get_orig_dialstring(p->chan_pvt);
00211 }
00212 ast_log(LOG_ERROR, "get_orig_dialstring callback not defined\n");
00213 return "";
00214 }
00215
00216 #if defined(HAVE_PRI_CCSS)
00217 static void sig_pri_make_cc_dialstring(struct sig_pri_chan *p, char *buf, size_t buf_size)
00218 {
00219 if (p->calls->make_cc_dialstring) {
00220 p->calls->make_cc_dialstring(p->chan_pvt, buf, buf_size);
00221 } else {
00222 ast_log(LOG_ERROR, "make_cc_dialstring callback not defined\n");
00223 buf[0] = '\0';
00224 }
00225 }
00226 #endif
00227
00228 static void sig_pri_dial_digits(struct sig_pri_chan *p, const char *dial_string)
00229 {
00230 if (p->calls->dial_digits) {
00231 p->calls->dial_digits(p->chan_pvt, dial_string);
00232 }
00233 }
00234
00235
00236
00237
00238
00239
00240
00241
00242
00243
00244
00245
00246 static void sig_pri_span_devstate_changed(struct sig_pri_span *pri)
00247 {
00248 if (pri->calls->update_span_devstate) {
00249 pri->calls->update_span_devstate(pri);
00250 }
00251 }
00252
00253
00254
00255
00256
00257
00258
00259
00260
00261
00262 static void sig_pri_set_caller_id(struct sig_pri_chan *p)
00263 {
00264 struct ast_party_caller caller;
00265
00266 if (p->calls->set_callerid) {
00267 ast_party_caller_init(&caller);
00268
00269 caller.id.name.str = p->cid_name;
00270 caller.id.name.presentation = p->callingpres;
00271 caller.id.name.valid = 1;
00272
00273 caller.id.number.str = p->cid_num;
00274 caller.id.number.plan = p->cid_ton;
00275 caller.id.number.presentation = p->callingpres;
00276 caller.id.number.valid = 1;
00277
00278 if (!ast_strlen_zero(p->cid_subaddr)) {
00279 caller.id.subaddress.valid = 1;
00280
00281
00282 caller.id.subaddress.str = p->cid_subaddr;
00283 }
00284 caller.id.tag = p->user_tag;
00285
00286 caller.ani.number.str = p->cid_ani;
00287
00288
00289 caller.ani.number.valid = 1;
00290
00291 caller.ani2 = p->cid_ani2;
00292 p->calls->set_callerid(p->chan_pvt, &caller);
00293 }
00294 }
00295
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306 static void sig_pri_set_dnid(struct sig_pri_chan *p, const char *dnid)
00307 {
00308 if (p->calls->set_dnid) {
00309 p->calls->set_dnid(p->chan_pvt, dnid);
00310 }
00311 }
00312
00313
00314
00315
00316
00317
00318
00319
00320
00321
00322
00323 static void sig_pri_set_rdnis(struct sig_pri_chan *p, const char *rdnis)
00324 {
00325 if (p->calls->set_rdnis) {
00326 p->calls->set_rdnis(p->chan_pvt, rdnis);
00327 }
00328 }
00329
00330 static void sig_pri_unlock_private(struct sig_pri_chan *p)
00331 {
00332 if (p->calls->unlock_private)
00333 p->calls->unlock_private(p->chan_pvt);
00334 }
00335
00336 static void sig_pri_lock_private(struct sig_pri_chan *p)
00337 {
00338 if (p->calls->lock_private)
00339 p->calls->lock_private(p->chan_pvt);
00340 }
00341
00342 static inline int pri_grab(struct sig_pri_chan *p, struct sig_pri_span *pri)
00343 {
00344
00345 while (ast_mutex_trylock(&pri->lock)) {
00346
00347 sig_pri_unlock_private(p);
00348 sched_yield();
00349 sig_pri_lock_private(p);
00350 }
00351
00352 if (pri->master != AST_PTHREADT_NULL) {
00353 pthread_kill(pri->master, SIGURG);
00354 }
00355 return 0;
00356 }
00357
00358
00359
00360
00361
00362
00363
00364
00365
00366
00367 static enum AST_REDIRECTING_REASON pri_to_ast_reason(int pri_reason)
00368 {
00369 enum AST_REDIRECTING_REASON ast_reason;
00370
00371 switch (pri_reason) {
00372 case PRI_REDIR_FORWARD_ON_BUSY:
00373 ast_reason = AST_REDIRECTING_REASON_USER_BUSY;
00374 break;
00375 case PRI_REDIR_FORWARD_ON_NO_REPLY:
00376 ast_reason = AST_REDIRECTING_REASON_NO_ANSWER;
00377 break;
00378 case PRI_REDIR_DEFLECTION:
00379 ast_reason = AST_REDIRECTING_REASON_DEFLECTION;
00380 break;
00381 case PRI_REDIR_UNCONDITIONAL:
00382 ast_reason = AST_REDIRECTING_REASON_UNCONDITIONAL;
00383 break;
00384 case PRI_REDIR_UNKNOWN:
00385 default:
00386 ast_reason = AST_REDIRECTING_REASON_UNKNOWN;
00387 break;
00388 }
00389
00390 return ast_reason;
00391 }
00392
00393
00394
00395
00396
00397
00398
00399
00400
00401
00402 static int ast_to_pri_reason(enum AST_REDIRECTING_REASON ast_reason)
00403 {
00404 int pri_reason;
00405
00406 switch (ast_reason) {
00407 case AST_REDIRECTING_REASON_USER_BUSY:
00408 pri_reason = PRI_REDIR_FORWARD_ON_BUSY;
00409 break;
00410 case AST_REDIRECTING_REASON_NO_ANSWER:
00411 pri_reason = PRI_REDIR_FORWARD_ON_NO_REPLY;
00412 break;
00413 case AST_REDIRECTING_REASON_UNCONDITIONAL:
00414 pri_reason = PRI_REDIR_UNCONDITIONAL;
00415 break;
00416 case AST_REDIRECTING_REASON_DEFLECTION:
00417 pri_reason = PRI_REDIR_DEFLECTION;
00418 break;
00419 case AST_REDIRECTING_REASON_UNKNOWN:
00420 default:
00421 pri_reason = PRI_REDIR_UNKNOWN;
00422 break;
00423 }
00424
00425 return pri_reason;
00426 }
00427
00428
00429
00430
00431
00432
00433
00434
00435
00436
00437 static int pri_to_ast_presentation(int pri_presentation)
00438 {
00439 int ast_presentation;
00440
00441 switch (pri_presentation) {
00442 case PRI_PRES_ALLOWED | PRI_PRES_USER_NUMBER_UNSCREENED:
00443 ast_presentation = AST_PRES_ALLOWED | AST_PRES_USER_NUMBER_UNSCREENED;
00444 break;
00445 case PRI_PRES_ALLOWED | PRI_PRES_USER_NUMBER_PASSED_SCREEN:
00446 ast_presentation = AST_PRES_ALLOWED | AST_PRES_USER_NUMBER_PASSED_SCREEN;
00447 break;
00448 case PRI_PRES_ALLOWED | PRI_PRES_USER_NUMBER_FAILED_SCREEN:
00449 ast_presentation = AST_PRES_ALLOWED | AST_PRES_USER_NUMBER_FAILED_SCREEN;
00450 break;
00451 case PRI_PRES_ALLOWED | PRI_PRES_NETWORK_NUMBER:
00452 ast_presentation = AST_PRES_ALLOWED | AST_PRES_NETWORK_NUMBER;
00453 break;
00454
00455 case PRI_PRES_RESTRICTED | PRI_PRES_USER_NUMBER_UNSCREENED:
00456 ast_presentation = AST_PRES_RESTRICTED | AST_PRES_USER_NUMBER_UNSCREENED;
00457 break;
00458 case PRI_PRES_RESTRICTED | PRI_PRES_USER_NUMBER_PASSED_SCREEN:
00459 ast_presentation = AST_PRES_RESTRICTED | AST_PRES_USER_NUMBER_PASSED_SCREEN;
00460 break;
00461 case PRI_PRES_RESTRICTED | PRI_PRES_USER_NUMBER_FAILED_SCREEN:
00462 ast_presentation = AST_PRES_RESTRICTED | AST_PRES_USER_NUMBER_FAILED_SCREEN;
00463 break;
00464 case PRI_PRES_RESTRICTED | PRI_PRES_NETWORK_NUMBER:
00465 ast_presentation = AST_PRES_RESTRICTED | AST_PRES_NETWORK_NUMBER;
00466 break;
00467
00468 case PRI_PRES_UNAVAILABLE | PRI_PRES_USER_NUMBER_UNSCREENED:
00469 case PRI_PRES_UNAVAILABLE | PRI_PRES_USER_NUMBER_PASSED_SCREEN:
00470 case PRI_PRES_UNAVAILABLE | PRI_PRES_USER_NUMBER_FAILED_SCREEN:
00471 case PRI_PRES_UNAVAILABLE | PRI_PRES_NETWORK_NUMBER:
00472 ast_presentation = AST_PRES_NUMBER_NOT_AVAILABLE;
00473 break;
00474
00475 default:
00476 ast_presentation = AST_PRES_RESTRICTED | AST_PRES_USER_NUMBER_UNSCREENED;
00477 break;
00478 }
00479
00480 return ast_presentation;
00481 }
00482
00483
00484
00485
00486
00487
00488
00489
00490
00491
00492 static int ast_to_pri_presentation(int ast_presentation)
00493 {
00494 int pri_presentation;
00495
00496 switch (ast_presentation) {
00497 case AST_PRES_ALLOWED | AST_PRES_USER_NUMBER_UNSCREENED:
00498 pri_presentation = PRI_PRES_ALLOWED | PRI_PRES_USER_NUMBER_UNSCREENED;
00499 break;
00500 case AST_PRES_ALLOWED | AST_PRES_USER_NUMBER_PASSED_SCREEN:
00501 pri_presentation = PRI_PRES_ALLOWED | PRI_PRES_USER_NUMBER_PASSED_SCREEN;
00502 break;
00503 case AST_PRES_ALLOWED | AST_PRES_USER_NUMBER_FAILED_SCREEN:
00504 pri_presentation = PRI_PRES_ALLOWED | PRI_PRES_USER_NUMBER_FAILED_SCREEN;
00505 break;
00506 case AST_PRES_ALLOWED | AST_PRES_NETWORK_NUMBER:
00507 pri_presentation = PRI_PRES_ALLOWED | PRI_PRES_NETWORK_NUMBER;
00508 break;
00509
00510 case AST_PRES_RESTRICTED | AST_PRES_USER_NUMBER_UNSCREENED:
00511 pri_presentation = PRI_PRES_RESTRICTED | PRI_PRES_USER_NUMBER_UNSCREENED;
00512 break;
00513 case AST_PRES_RESTRICTED | AST_PRES_USER_NUMBER_PASSED_SCREEN:
00514 pri_presentation = PRI_PRES_RESTRICTED | PRI_PRES_USER_NUMBER_PASSED_SCREEN;
00515 break;
00516 case AST_PRES_RESTRICTED | AST_PRES_USER_NUMBER_FAILED_SCREEN:
00517 pri_presentation = PRI_PRES_RESTRICTED | PRI_PRES_USER_NUMBER_FAILED_SCREEN;
00518 break;
00519 case AST_PRES_RESTRICTED | AST_PRES_NETWORK_NUMBER:
00520 pri_presentation = PRI_PRES_RESTRICTED | PRI_PRES_NETWORK_NUMBER;
00521 break;
00522
00523 case AST_PRES_UNAVAILABLE | AST_PRES_USER_NUMBER_UNSCREENED:
00524 case AST_PRES_UNAVAILABLE | AST_PRES_USER_NUMBER_PASSED_SCREEN:
00525 case AST_PRES_UNAVAILABLE | AST_PRES_USER_NUMBER_FAILED_SCREEN:
00526 case AST_PRES_UNAVAILABLE | AST_PRES_NETWORK_NUMBER:
00527 pri_presentation = PRES_NUMBER_NOT_AVAILABLE;
00528 break;
00529
00530 default:
00531 pri_presentation = PRI_PRES_RESTRICTED | PRI_PRES_USER_NUMBER_UNSCREENED;
00532 break;
00533 }
00534
00535 return pri_presentation;
00536 }
00537
00538
00539
00540
00541
00542
00543
00544
00545
00546
00547 static enum AST_PARTY_CHAR_SET pri_to_ast_char_set(int pri_char_set)
00548 {
00549 enum AST_PARTY_CHAR_SET ast_char_set;
00550
00551 switch (pri_char_set) {
00552 default:
00553 case PRI_CHAR_SET_UNKNOWN:
00554 ast_char_set = AST_PARTY_CHAR_SET_UNKNOWN;
00555 break;
00556 case PRI_CHAR_SET_ISO8859_1:
00557 ast_char_set = AST_PARTY_CHAR_SET_ISO8859_1;
00558 break;
00559 case PRI_CHAR_SET_WITHDRAWN:
00560 ast_char_set = AST_PARTY_CHAR_SET_WITHDRAWN;
00561 break;
00562 case PRI_CHAR_SET_ISO8859_2:
00563 ast_char_set = AST_PARTY_CHAR_SET_ISO8859_2;
00564 break;
00565 case PRI_CHAR_SET_ISO8859_3:
00566 ast_char_set = AST_PARTY_CHAR_SET_ISO8859_3;
00567 break;
00568 case PRI_CHAR_SET_ISO8859_4:
00569 ast_char_set = AST_PARTY_CHAR_SET_ISO8859_4;
00570 break;
00571 case PRI_CHAR_SET_ISO8859_5:
00572 ast_char_set = AST_PARTY_CHAR_SET_ISO8859_5;
00573 break;
00574 case PRI_CHAR_SET_ISO8859_7:
00575 ast_char_set = AST_PARTY_CHAR_SET_ISO8859_7;
00576 break;
00577 case PRI_CHAR_SET_ISO10646_BMPSTRING:
00578 ast_char_set = AST_PARTY_CHAR_SET_ISO10646_BMPSTRING;
00579 break;
00580 case PRI_CHAR_SET_ISO10646_UTF_8STRING:
00581 ast_char_set = AST_PARTY_CHAR_SET_ISO10646_UTF_8STRING;
00582 break;
00583 }
00584
00585 return ast_char_set;
00586 }
00587
00588
00589
00590
00591
00592
00593
00594
00595
00596
00597 static int ast_to_pri_char_set(enum AST_PARTY_CHAR_SET ast_char_set)
00598 {
00599 int pri_char_set;
00600
00601 switch (ast_char_set) {
00602 default:
00603 case AST_PARTY_CHAR_SET_UNKNOWN:
00604 pri_char_set = PRI_CHAR_SET_UNKNOWN;
00605 break;
00606 case AST_PARTY_CHAR_SET_ISO8859_1:
00607 pri_char_set = PRI_CHAR_SET_ISO8859_1;
00608 break;
00609 case AST_PARTY_CHAR_SET_WITHDRAWN:
00610 pri_char_set = PRI_CHAR_SET_WITHDRAWN;
00611 break;
00612 case AST_PARTY_CHAR_SET_ISO8859_2:
00613 pri_char_set = PRI_CHAR_SET_ISO8859_2;
00614 break;
00615 case AST_PARTY_CHAR_SET_ISO8859_3:
00616 pri_char_set = PRI_CHAR_SET_ISO8859_3;
00617 break;
00618 case AST_PARTY_CHAR_SET_ISO8859_4:
00619 pri_char_set = PRI_CHAR_SET_ISO8859_4;
00620 break;
00621 case AST_PARTY_CHAR_SET_ISO8859_5:
00622 pri_char_set = PRI_CHAR_SET_ISO8859_5;
00623 break;
00624 case AST_PARTY_CHAR_SET_ISO8859_7:
00625 pri_char_set = PRI_CHAR_SET_ISO8859_7;
00626 break;
00627 case AST_PARTY_CHAR_SET_ISO10646_BMPSTRING:
00628 pri_char_set = PRI_CHAR_SET_ISO10646_BMPSTRING;
00629 break;
00630 case AST_PARTY_CHAR_SET_ISO10646_UTF_8STRING:
00631 pri_char_set = PRI_CHAR_SET_ISO10646_UTF_8STRING;
00632 break;
00633 }
00634
00635 return pri_char_set;
00636 }
00637
00638 #if defined(HAVE_PRI_SUBADDR)
00639
00640
00641
00642
00643
00644
00645
00646
00647
00648
00649
00650 static void sig_pri_set_subaddress(struct ast_party_subaddress *ast_subaddress, const struct pri_party_subaddress *pri_subaddress)
00651 {
00652 char *cnum, *ptr;
00653 int x, len;
00654
00655 if (ast_subaddress->str) {
00656 ast_free(ast_subaddress->str);
00657 }
00658 if (pri_subaddress->length <= 0) {
00659 ast_party_subaddress_init(ast_subaddress);
00660 return;
00661 }
00662
00663 if (!pri_subaddress->type) {
00664
00665 ast_subaddress->str = ast_strdup((char *) pri_subaddress->data);
00666 } else {
00667
00668 if (!(cnum = ast_malloc(2 * pri_subaddress->length + 1))) {
00669 ast_party_subaddress_init(ast_subaddress);
00670 return;
00671 }
00672
00673 ptr = cnum;
00674 len = pri_subaddress->length - 1;
00675 for (x = 0; x < len; ++x) {
00676 ptr += sprintf(ptr, "%02x", pri_subaddress->data[x]);
00677 }
00678
00679 if (pri_subaddress->odd_even_indicator) {
00680
00681 sprintf(ptr, "%01x", (pri_subaddress->data[len]) >> 4);
00682 } else {
00683
00684 sprintf(ptr, "%02x", pri_subaddress->data[len]);
00685 }
00686 ast_subaddress->str = cnum;
00687 }
00688 ast_subaddress->type = pri_subaddress->type;
00689 ast_subaddress->odd_even_indicator = pri_subaddress->odd_even_indicator;
00690 ast_subaddress->valid = 1;
00691 }
00692 #endif
00693
00694 #if defined(HAVE_PRI_SUBADDR)
00695 static unsigned char ast_pri_pack_hex_char(char c)
00696 {
00697 unsigned char res;
00698
00699 if (c < '0') {
00700 res = 0;
00701 } else if (c < ('9' + 1)) {
00702 res = c - '0';
00703 } else if (c < 'A') {
00704 res = 0;
00705 } else if (c < ('F' + 1)) {
00706 res = c - 'A' + 10;
00707 } else if (c < 'a') {
00708 res = 0;
00709 } else if (c < ('f' + 1)) {
00710 res = c - 'a' + 10;
00711 } else {
00712 res = 0;
00713 }
00714 return res;
00715 }
00716 #endif
00717
00718 #if defined(HAVE_PRI_SUBADDR)
00719
00720
00721
00722
00723
00724
00725
00726
00727
00728
00729
00730
00731
00732
00733
00734 static int ast_pri_pack_hex_string(unsigned char *dst, char *src, int maxlen)
00735 {
00736 int res = 0;
00737 int len = strlen(src);
00738
00739 if (len > (2 * maxlen)) {
00740 len = 2 * maxlen;
00741 }
00742
00743 res = len / 2 + len % 2;
00744
00745 while (len > 1) {
00746 *dst = ast_pri_pack_hex_char(*src) << 4;
00747 src++;
00748 *dst |= ast_pri_pack_hex_char(*src);
00749 dst++, src++;
00750 len -= 2;
00751 }
00752 if (len) {
00753 *dst = ast_pri_pack_hex_char(*src) << 4;
00754 }
00755 return res;
00756 }
00757 #endif
00758
00759 #if defined(HAVE_PRI_SUBADDR)
00760
00761
00762
00763
00764
00765
00766
00767
00768
00769
00770
00771
00772 static void sig_pri_party_subaddress_from_ast(struct pri_party_subaddress *pri_subaddress, const struct ast_party_subaddress *ast_subaddress)
00773 {
00774 if (ast_subaddress->valid && !ast_strlen_zero(ast_subaddress->str)) {
00775 pri_subaddress->type = ast_subaddress->type;
00776 if (!ast_subaddress->type) {
00777
00778 ast_copy_string((char *) pri_subaddress->data, ast_subaddress->str,
00779 sizeof(pri_subaddress->data));
00780 pri_subaddress->length = strlen((char *) pri_subaddress->data);
00781 pri_subaddress->odd_even_indicator = 0;
00782 pri_subaddress->valid = 1;
00783 } else {
00784
00785
00786
00787
00788
00789 int length = ast_pri_pack_hex_string(pri_subaddress->data,
00790 ast_subaddress->str, sizeof(pri_subaddress->data));
00791
00792 pri_subaddress->length = length;
00793
00794 length = strlen(ast_subaddress->str);
00795 if (length > 2 * sizeof(pri_subaddress->data)) {
00796 pri_subaddress->odd_even_indicator = 0;
00797 } else {
00798 pri_subaddress->odd_even_indicator = (length & 1);
00799 }
00800 pri_subaddress->valid = 1;
00801 }
00802 }
00803 }
00804 #endif
00805
00806
00807
00808
00809
00810
00811
00812
00813
00814
00815
00816
00817
00818 static void sig_pri_party_name_from_ast(struct pri_party_name *pri_name, const struct ast_party_name *ast_name)
00819 {
00820 if (!ast_name->valid) {
00821 return;
00822 }
00823 pri_name->valid = 1;
00824 pri_name->presentation = ast_to_pri_presentation(ast_name->presentation);
00825 pri_name->char_set = ast_to_pri_char_set(ast_name->char_set);
00826 if (!ast_strlen_zero(ast_name->str)) {
00827 ast_copy_string(pri_name->str, ast_name->str, sizeof(pri_name->str));
00828 }
00829 }
00830
00831
00832
00833
00834
00835
00836
00837
00838
00839
00840
00841
00842
00843 static void sig_pri_party_number_from_ast(struct pri_party_number *pri_number, const struct ast_party_number *ast_number)
00844 {
00845 if (!ast_number->valid) {
00846 return;
00847 }
00848 pri_number->valid = 1;
00849 pri_number->presentation = ast_to_pri_presentation(ast_number->presentation);
00850 pri_number->plan = ast_number->plan;
00851 if (!ast_strlen_zero(ast_number->str)) {
00852 ast_copy_string(pri_number->str, ast_number->str, sizeof(pri_number->str));
00853 }
00854 }
00855
00856
00857
00858
00859
00860
00861
00862
00863
00864
00865
00866
00867
00868 static void sig_pri_party_id_from_ast(struct pri_party_id *pri_id, const struct ast_party_id *ast_id)
00869 {
00870 sig_pri_party_name_from_ast(&pri_id->name, &ast_id->name);
00871 sig_pri_party_number_from_ast(&pri_id->number, &ast_id->number);
00872 #if defined(HAVE_PRI_SUBADDR)
00873 sig_pri_party_subaddress_from_ast(&pri_id->subaddress, &ast_id->subaddress);
00874 #endif
00875 }
00876
00877
00878
00879
00880
00881
00882
00883
00884
00885
00886
00887
00888
00889 static void sig_pri_redirecting_update(struct sig_pri_chan *pvt, struct ast_channel *ast)
00890 {
00891 struct pri_party_redirecting pri_redirecting;
00892
00893
00894
00895 memset(&pri_redirecting, 0, sizeof(pri_redirecting));
00896 sig_pri_party_id_from_ast(&pri_redirecting.from, &ast->redirecting.from);
00897 sig_pri_party_id_from_ast(&pri_redirecting.to, &ast->redirecting.to);
00898 pri_redirecting.count = ast->redirecting.count;
00899 pri_redirecting.reason = ast_to_pri_reason(ast->redirecting.reason);
00900
00901 pri_redirecting_update(pvt->pri->pri, pvt->call, &pri_redirecting);
00902 }
00903
00904
00905
00906
00907
00908
00909
00910
00911
00912
00913 static void sig_pri_dsp_reset_and_flush_digits(struct sig_pri_chan *p)
00914 {
00915 if (p->calls->dsp_reset_and_flush_digits) {
00916 p->calls->dsp_reset_and_flush_digits(p->chan_pvt);
00917 }
00918 }
00919
00920 static int sig_pri_set_echocanceller(struct sig_pri_chan *p, int enable)
00921 {
00922 if (p->calls->set_echocanceller)
00923 return p->calls->set_echocanceller(p->chan_pvt, enable);
00924 else
00925 return -1;
00926 }
00927
00928 static void sig_pri_fixup_chans(struct sig_pri_chan *old_chan, struct sig_pri_chan *new_chan)
00929 {
00930 if (old_chan->calls->fixup_chans)
00931 old_chan->calls->fixup_chans(old_chan->chan_pvt, new_chan->chan_pvt);
00932 }
00933
00934 static int sig_pri_play_tone(struct sig_pri_chan *p, enum sig_pri_tone tone)
00935 {
00936 if (p->calls->play_tone)
00937 return p->calls->play_tone(p->chan_pvt, tone);
00938 else
00939 return -1;
00940 }
00941
00942 static struct ast_channel *sig_pri_new_ast_channel(struct sig_pri_chan *p, int state, int ulaw, int transfercapability, char *exten, const struct ast_channel *requestor)
00943 {
00944 struct ast_channel *c;
00945
00946 if (p->calls->new_ast_channel) {
00947 c = p->calls->new_ast_channel(p->chan_pvt, state, ulaw, exten, requestor);
00948 } else {
00949 return NULL;
00950 }
00951 if (!c) {
00952 return NULL;
00953 }
00954
00955 if (!p->owner)
00956 p->owner = c;
00957 p->isidlecall = 0;
00958 p->alreadyhungup = 0;
00959 c->transfercapability = transfercapability;
00960 pbx_builtin_setvar_helper(c, "TRANSFERCAPABILITY",
00961 ast_transfercapability2str(transfercapability));
00962 if (transfercapability & AST_TRANS_CAP_DIGITAL) {
00963 sig_pri_set_digital(p, 1);
00964 }
00965 if (p->pri) {
00966 ast_mutex_lock(&p->pri->lock);
00967 sig_pri_span_devstate_changed(p->pri);
00968 ast_mutex_unlock(&p->pri->lock);
00969 }
00970
00971 return c;
00972 }
00973
00974
00975
00976
00977
00978
00979
00980
00981
00982
00983 static void sig_pri_open_media(struct sig_pri_chan *p)
00984 {
00985 if (p->no_b_channel) {
00986 return;
00987 }
00988
00989 if (p->calls->open_media) {
00990 p->calls->open_media(p->chan_pvt);
00991 }
00992 }
00993
00994
00995
00996
00997
00998
00999
01000
01001
01002
01003
01004
01005 static void sig_pri_ami_channel_event(struct sig_pri_chan *p)
01006 {
01007 if (p->calls->ami_channel_event) {
01008 p->calls->ami_channel_event(p->chan_pvt, p->owner);
01009 }
01010 }
01011
01012 struct ast_channel *sig_pri_request(struct sig_pri_chan *p, enum sig_pri_law law, const struct ast_channel *requestor, int transfercapability)
01013 {
01014 struct ast_channel *ast;
01015
01016 ast_log(LOG_DEBUG, "%s %d\n", __FUNCTION__, p->channel);
01017
01018 sig_pri_set_outgoing(p, 1);
01019 ast = sig_pri_new_ast_channel(p, AST_STATE_RESERVED, law, transfercapability, p->exten, requestor);
01020 if (!ast) {
01021 sig_pri_set_outgoing(p, 0);
01022 }
01023 return ast;
01024 }
01025
01026 int pri_is_up(struct sig_pri_span *pri)
01027 {
01028 int x;
01029 for (x = 0; x < SIG_PRI_NUM_DCHANS; x++) {
01030 if (pri->dchanavail[x] == DCHAN_AVAILABLE)
01031 return 1;
01032 }
01033 return 0;
01034 }
01035
01036 static const char *pri_order(int level)
01037 {
01038 switch (level) {
01039 case 0:
01040 return "Primary";
01041 case 1:
01042 return "Secondary";
01043 case 2:
01044 return "Tertiary";
01045 case 3:
01046 return "Quaternary";
01047 default:
01048 return "<Unknown>";
01049 }
01050 }
01051
01052
01053 static int pri_active_dchan_index(struct sig_pri_span *pri)
01054 {
01055 int x;
01056
01057 for (x = 0; x < SIG_PRI_NUM_DCHANS; x++) {
01058 if ((pri->dchans[x] == pri->pri))
01059 return x;
01060 }
01061
01062 ast_log(LOG_WARNING, "No active dchan found!\n");
01063 return -1;
01064 }
01065
01066 static void pri_find_dchan(struct sig_pri_span *pri)
01067 {
01068 struct pri *old;
01069 int oldslot = -1;
01070 int newslot = -1;
01071 int idx;
01072
01073 old = pri->pri;
01074 for (idx = 0; idx < SIG_PRI_NUM_DCHANS; ++idx) {
01075 if (!pri->dchans[idx]) {
01076
01077 break;
01078 }
01079 if (pri->dchans[idx] == old) {
01080 oldslot = idx;
01081 }
01082 if (newslot < 0 && pri->dchanavail[idx] == DCHAN_AVAILABLE) {
01083 newslot = idx;
01084 }
01085 }
01086
01087
01088 if (1 < idx) {
01089
01090 if (newslot < 0) {
01091
01092 newslot = 0;
01093
01094 if (!pri->no_d_channels) {
01095 pri->no_d_channels = 1;
01096 if (old && oldslot != newslot) {
01097 ast_log(LOG_WARNING,
01098 "Span %d: No D-channels up! Switching selected D-channel from %s to %s.\n",
01099 pri->span, pri_order(oldslot), pri_order(newslot));
01100 } else {
01101 ast_log(LOG_WARNING, "Span %d: No D-channels up!\n", pri->span);
01102 }
01103 }
01104 } else {
01105 pri->no_d_channels = 0;
01106 }
01107 if (old && oldslot != newslot) {
01108 ast_log(LOG_NOTICE,
01109 "Switching selected D-channel from %s (fd %d) to %s (fd %d)!\n",
01110 pri_order(oldslot), pri->fds[oldslot],
01111 pri_order(newslot), pri->fds[newslot]);
01112 }
01113 } else {
01114 if (newslot < 0) {
01115
01116 newslot = 0;
01117
01118 if (!pri->no_d_channels) {
01119 pri->no_d_channels = 1;
01120
01121
01122
01123
01124
01125 if (pri->sig != SIG_BRI_PTMP) {
01126 ast_log(LOG_WARNING, "Span %d: D-channel is down!\n", pri->span);
01127 }
01128 }
01129 } else {
01130 pri->no_d_channels = 0;
01131 }
01132 }
01133 pri->pri = pri->dchans[newslot];
01134 }
01135
01136
01137
01138
01139
01140
01141
01142
01143
01144
01145 static int sig_pri_is_chan_in_use(struct sig_pri_chan *pvt)
01146 {
01147 return pvt->owner || pvt->call || pvt->allocated || pvt->inalarm
01148 || pvt->resetting != SIG_PRI_RESET_IDLE;
01149 }
01150
01151
01152
01153
01154
01155
01156
01157
01158
01159 int sig_pri_is_chan_available(struct sig_pri_chan *pvt)
01160 {
01161 return !sig_pri_is_chan_in_use(pvt)
01162 #if defined(HAVE_PRI_SERVICE_MESSAGES)
01163
01164 && !pvt->service_status
01165 #endif
01166 ;
01167 }
01168
01169
01170
01171
01172
01173
01174
01175
01176
01177
01178
01179
01180
01181
01182 static void sig_pri_lock_owner(struct sig_pri_span *pri, int chanpos)
01183 {
01184 for (;;) {
01185 if (!pri->pvts[chanpos]->owner) {
01186
01187 break;
01188 }
01189 if (!ast_channel_trylock(pri->pvts[chanpos]->owner)) {
01190
01191 break;
01192 }
01193
01194
01195 sig_pri_unlock_private(pri->pvts[chanpos]);
01196 DEADLOCK_AVOIDANCE(&pri->lock);
01197 sig_pri_lock_private(pri->pvts[chanpos]);
01198 }
01199 }
01200
01201
01202
01203
01204
01205
01206
01207
01208
01209
01210
01211
01212
01213
01214
01215 static void pri_queue_frame(struct sig_pri_span *pri, int chanpos, struct ast_frame *frame)
01216 {
01217 sig_pri_lock_owner(pri, chanpos);
01218 if (pri->pvts[chanpos]->owner) {
01219 ast_queue_frame(pri->pvts[chanpos]->owner, frame);
01220 ast_channel_unlock(pri->pvts[chanpos]->owner);
01221 }
01222 }
01223
01224
01225
01226
01227
01228
01229
01230
01231
01232
01233
01234
01235
01236
01237
01238 static void pri_queue_control(struct sig_pri_span *pri, int chanpos, int subclass)
01239 {
01240 struct ast_frame f = {AST_FRAME_CONTROL, };
01241 struct sig_pri_chan *p = pri->pvts[chanpos];
01242
01243 if (p->calls->queue_control) {
01244 p->calls->queue_control(p->chan_pvt, subclass);
01245 }
01246
01247 f.subclass.integer = subclass;
01248 pri_queue_frame(pri, chanpos, &f);
01249 }
01250
01251
01252
01253
01254
01255
01256
01257
01258
01259
01260
01261
01262
01263
01264 static int pri_find_principle_by_call(struct sig_pri_span *pri, q931_call *call)
01265 {
01266 int idx;
01267
01268 if (!call) {
01269
01270 return -1;
01271 }
01272 for (idx = 0; idx < pri->numchans; ++idx) {
01273 if (pri->pvts[idx] && pri->pvts[idx]->call == call) {
01274
01275 return idx;
01276 }
01277 }
01278 return -1;
01279 }
01280
01281
01282
01283
01284
01285
01286
01287
01288
01289
01290
01291
01292
01293
01294 static void sig_pri_kill_call(struct sig_pri_span *pri, q931_call *call, int cause)
01295 {
01296 int chanpos;
01297
01298 chanpos = pri_find_principle_by_call(pri, call);
01299 if (chanpos < 0) {
01300 pri_hangup(pri->pri, call, cause);
01301 return;
01302 }
01303 sig_pri_lock_private(pri->pvts[chanpos]);
01304 if (!pri->pvts[chanpos]->owner) {
01305 pri_hangup(pri->pri, call, cause);
01306 pri->pvts[chanpos]->call = NULL;
01307 sig_pri_unlock_private(pri->pvts[chanpos]);
01308 sig_pri_span_devstate_changed(pri);
01309 return;
01310 }
01311 pri->pvts[chanpos]->owner->hangupcause = cause;
01312 pri_queue_control(pri, chanpos, AST_CONTROL_HANGUP);
01313 sig_pri_unlock_private(pri->pvts[chanpos]);
01314 }
01315
01316
01317
01318
01319
01320
01321
01322
01323
01324
01325
01326
01327
01328
01329 static int pri_find_principle(struct sig_pri_span *pri, int channel, q931_call *call)
01330 {
01331 int x;
01332 int span;
01333 int principle;
01334 int prioffset;
01335
01336 if (channel < 0) {
01337
01338 return -1;
01339 }
01340
01341 prioffset = PRI_CHANNEL(channel);
01342 if (!prioffset || (channel & PRI_HELD_CALL)) {
01343 if (!call) {
01344
01345 return -1;
01346 }
01347 principle = -1;
01348 for (x = 0; x < pri->numchans; ++x) {
01349 if (pri->pvts[x]
01350 && pri->pvts[x]->call == call) {
01351 principle = x;
01352 break;
01353 }
01354 }
01355 return principle;
01356 }
01357
01358 span = PRI_SPAN(channel);
01359 if (!(channel & PRI_EXPLICIT)) {
01360 int index;
01361
01362 index = pri_active_dchan_index(pri);
01363 if (index == -1) {
01364 return -1;
01365 }
01366 span = pri->dchan_logical_span[index];
01367 }
01368
01369 principle = -1;
01370 for (x = 0; x < pri->numchans; x++) {
01371 if (pri->pvts[x]
01372 && pri->pvts[x]->prioffset == prioffset
01373 && pri->pvts[x]->logicalspan == span
01374 && !pri->pvts[x]->no_b_channel) {
01375 principle = x;
01376 break;
01377 }
01378 }
01379
01380 return principle;
01381 }
01382
01383
01384
01385
01386
01387
01388
01389
01390
01391
01392
01393
01394
01395
01396 static int pri_fixup_principle(struct sig_pri_span *pri, int principle, q931_call *call)
01397 {
01398 int x;
01399
01400 if (principle < 0 || pri->numchans <= principle) {
01401
01402 return -1;
01403 }
01404 if (!call) {
01405
01406 return principle;
01407 }
01408 if (pri->pvts[principle] && pri->pvts[principle]->call == call) {
01409
01410 return principle;
01411 }
01412
01413
01414 for (x = 0; x < pri->numchans; x++) {
01415 struct sig_pri_chan *new_chan;
01416 struct sig_pri_chan *old_chan;
01417
01418 if (!pri->pvts[x] || pri->pvts[x]->call != call) {
01419 continue;
01420 }
01421
01422
01423 new_chan = pri->pvts[principle];
01424 old_chan = pri->pvts[x];
01425
01426
01427 sig_pri_lock_private(old_chan);
01428 sig_pri_lock_owner(pri, x);
01429 sig_pri_lock_private(new_chan);
01430
01431 ast_verb(3, "Moving call (%s) from channel %d to %d.\n",
01432 old_chan->owner ? old_chan->owner->name : "",
01433 old_chan->channel, new_chan->channel);
01434 if (!sig_pri_is_chan_available(new_chan)) {
01435 ast_log(LOG_WARNING,
01436 "Can't move call (%s) from channel %d to %d. It is already in use.\n",
01437 old_chan->owner ? old_chan->owner->name : "",
01438 old_chan->channel, new_chan->channel);
01439 sig_pri_unlock_private(new_chan);
01440 if (old_chan->owner) {
01441 ast_channel_unlock(old_chan->owner);
01442 }
01443 sig_pri_unlock_private(old_chan);
01444 return -1;
01445 }
01446
01447 sig_pri_fixup_chans(old_chan, new_chan);
01448
01449
01450 new_chan->owner = old_chan->owner;
01451 old_chan->owner = NULL;
01452
01453 new_chan->call = old_chan->call;
01454 old_chan->call = NULL;
01455
01456
01457 #if defined(HAVE_PRI_AOC_EVENTS)
01458 new_chan->aoc_s_request_invoke_id_valid = old_chan->aoc_s_request_invoke_id_valid;
01459 new_chan->waiting_for_aoce = old_chan->waiting_for_aoce;
01460 new_chan->holding_aoce = old_chan->holding_aoce;
01461 #endif
01462 new_chan->alreadyhungup = old_chan->alreadyhungup;
01463 new_chan->isidlecall = old_chan->isidlecall;
01464 new_chan->progress = old_chan->progress;
01465 new_chan->allocated = old_chan->allocated;
01466 new_chan->outgoing = old_chan->outgoing;
01467 new_chan->digital = old_chan->digital;
01468 #if defined(HAVE_PRI_CALL_WAITING)
01469 new_chan->is_call_waiting = old_chan->is_call_waiting;
01470 #endif
01471
01472 #if defined(HAVE_PRI_AOC_EVENTS)
01473 old_chan->aoc_s_request_invoke_id_valid = 0;
01474 old_chan->waiting_for_aoce = 0;
01475 old_chan->holding_aoce = 0;
01476 #endif
01477 old_chan->alreadyhungup = 0;
01478 old_chan->isidlecall = 0;
01479 old_chan->progress = 0;
01480 old_chan->allocated = 0;
01481 old_chan->outgoing = 0;
01482 old_chan->digital = 0;
01483 #if defined(HAVE_PRI_CALL_WAITING)
01484 old_chan->is_call_waiting = 0;
01485 #endif
01486
01487
01488 new_chan->call_level = old_chan->call_level;
01489 old_chan->call_level = SIG_PRI_CALL_LEVEL_IDLE;
01490 #if defined(HAVE_PRI_REVERSE_CHARGE)
01491 new_chan->reverse_charging_indication = old_chan->reverse_charging_indication;
01492 #endif
01493 #if defined(HAVE_PRI_SETUP_KEYPAD)
01494 strcpy(new_chan->keypad_digits, old_chan->keypad_digits);
01495 #endif
01496 strcpy(new_chan->deferred_digits, old_chan->deferred_digits);
01497 #if defined(HAVE_PRI_AOC_EVENTS)
01498 new_chan->aoc_s_request_invoke_id = old_chan->aoc_s_request_invoke_id;
01499 new_chan->aoc_e = old_chan->aoc_e;
01500 #endif
01501 strcpy(new_chan->user_tag, old_chan->user_tag);
01502
01503 if (new_chan->no_b_channel) {
01504
01505 new_chan->hidecallerid = old_chan->hidecallerid;
01506 new_chan->hidecalleridname = old_chan->hidecalleridname;
01507 new_chan->immediate = old_chan->immediate;
01508 new_chan->priexclusive = old_chan->priexclusive;
01509 new_chan->priindication_oob = old_chan->priindication_oob;
01510 new_chan->use_callerid = old_chan->use_callerid;
01511 new_chan->use_callingpres = old_chan->use_callingpres;
01512 new_chan->stripmsd = old_chan->stripmsd;
01513 strcpy(new_chan->context, old_chan->context);
01514 strcpy(new_chan->mohinterpret, old_chan->mohinterpret);
01515
01516
01517 new_chan->logicalspan = old_chan->logicalspan;
01518 new_chan->mastertrunkgroup = old_chan->mastertrunkgroup;
01519 } else if (old_chan->no_b_channel) {
01520
01521
01522
01523
01524
01525
01526 sig_pri_open_media(new_chan);
01527 }
01528
01529 if (new_chan->owner) {
01530 sig_pri_ami_channel_event(new_chan);
01531 }
01532
01533 sig_pri_unlock_private(old_chan);
01534 if (new_chan->owner) {
01535 ast_channel_unlock(new_chan->owner);
01536 }
01537 sig_pri_unlock_private(new_chan);
01538
01539 return principle;
01540 }
01541 ast_verb(3, "Call specified, but not found.\n");
01542 return -1;
01543 }
01544
01545
01546
01547
01548
01549
01550
01551
01552
01553
01554
01555
01556
01557
01558
01559
01560
01561
01562
01563 static int pri_find_fixup_principle(struct sig_pri_span *pri, int channel, q931_call *call)
01564 {
01565 int chanpos;
01566
01567 chanpos = pri_find_principle(pri, channel, call);
01568 if (chanpos < 0) {
01569 ast_log(LOG_WARNING, "Span %d: PRI requested channel %d/%d is unconfigured.\n",
01570 pri->span, PRI_SPAN(channel), PRI_CHANNEL(channel));
01571 sig_pri_kill_call(pri, call, PRI_CAUSE_IDENTIFIED_CHANNEL_NOTEXIST);
01572 return -1;
01573 }
01574 chanpos = pri_fixup_principle(pri, chanpos, call);
01575 if (chanpos < 0) {
01576 ast_log(LOG_WARNING, "Span %d: PRI requested channel %d/%d is not available.\n",
01577 pri->span, PRI_SPAN(channel), PRI_CHANNEL(channel));
01578
01579
01580
01581
01582
01583
01584
01585 sig_pri_kill_call(pri, call, PRI_CAUSE_CHANNEL_UNACCEPTABLE);
01586 return -1;
01587 }
01588 return chanpos;
01589 }
01590
01591 static char * redirectingreason2str(int redirectingreason)
01592 {
01593 switch (redirectingreason) {
01594 case 0:
01595 return "UNKNOWN";
01596 case 1:
01597 return "BUSY";
01598 case 2:
01599 return "NO_REPLY";
01600 case 0xF:
01601 return "UNCONDITIONAL";
01602 default:
01603 return "NOREDIRECT";
01604 }
01605 }
01606
01607 static char *dialplan2str(int dialplan)
01608 {
01609 if (dialplan == -1) {
01610 return("Dynamically set dialplan in ISDN");
01611 }
01612 return (pri_plan2str(dialplan));
01613 }
01614
01615
01616
01617
01618
01619
01620
01621
01622
01623
01624
01625
01626
01627 static void apply_plan_to_number(char *buf, size_t size, const struct sig_pri_span *pri, const char *number, int plan)
01628 {
01629 switch (plan) {
01630 case PRI_INTERNATIONAL_ISDN:
01631 snprintf(buf, size, "%s%s", pri->internationalprefix, number);
01632 break;
01633 case PRI_NATIONAL_ISDN:
01634 snprintf(buf, size, "%s%s", pri->nationalprefix, number);
01635 break;
01636 case PRI_LOCAL_ISDN:
01637 snprintf(buf, size, "%s%s", pri->localprefix, number);
01638 break;
01639 case PRI_PRIVATE:
01640 snprintf(buf, size, "%s%s", pri->privateprefix, number);
01641 break;
01642 case PRI_UNKNOWN:
01643 snprintf(buf, size, "%s%s", pri->unknownprefix, number);
01644 break;
01645 default:
01646 snprintf(buf, size, "%s", number);
01647 break;
01648 }
01649 }
01650
01651
01652
01653
01654
01655
01656
01657
01658
01659
01660
01661
01662
01663 static void apply_plan_to_existing_number(char *buf, size_t size, const struct sig_pri_span *pri, const char *number, int plan)
01664 {
01665
01666 if (ast_strlen_zero(number)) {
01667 if (size) {
01668 *buf = '\0';
01669 }
01670 return;
01671 }
01672 apply_plan_to_number(buf, size, pri, number, plan);
01673 }
01674
01675
01676
01677
01678
01679
01680
01681
01682
01683
01684
01685 static void pri_check_restart(struct sig_pri_span *pri)
01686 {
01687 #if defined(HAVE_PRI_SERVICE_MESSAGES)
01688 unsigned why;
01689 #endif
01690
01691 for (++pri->resetpos; pri->resetpos < pri->numchans; ++pri->resetpos) {
01692 if (!pri->pvts[pri->resetpos]
01693 || pri->pvts[pri->resetpos]->no_b_channel
01694 || sig_pri_is_chan_in_use(pri->pvts[pri->resetpos])) {
01695 continue;
01696 }
01697 #if defined(HAVE_PRI_SERVICE_MESSAGES)
01698 why = pri->pvts[pri->resetpos]->service_status;
01699 if (why) {
01700 ast_log(LOG_NOTICE,
01701 "Span %d: channel %d out-of-service (reason: %s), not sending RESTART\n",
01702 pri->span, pri->pvts[pri->resetpos]->channel,
01703 (why & SRVST_FAREND) ? (why & SRVST_NEAREND) ? "both ends" : "far end" : "near end");
01704 continue;
01705 }
01706 #endif
01707 break;
01708 }
01709 if (pri->resetpos < pri->numchans) {
01710
01711 pri->pvts[pri->resetpos]->resetting = SIG_PRI_RESET_ACTIVE;
01712 pri_reset(pri->pri, PVT_TO_CHANNEL(pri->pvts[pri->resetpos]));
01713 } else {
01714 pri->resetting = 0;
01715 time(&pri->lastreset);
01716 sig_pri_span_devstate_changed(pri);
01717 }
01718 }
01719
01720 #if defined(HAVE_PRI_CALL_WAITING)
01721
01722
01723
01724
01725
01726
01727
01728
01729
01730
01731
01732
01733 static void sig_pri_init_config(struct sig_pri_chan *pvt, struct sig_pri_span *pri)
01734 {
01735 pvt->stripmsd = pri->ch_cfg.stripmsd;
01736 pvt->hidecallerid = pri->ch_cfg.hidecallerid;
01737 pvt->hidecalleridname = pri->ch_cfg.hidecalleridname;
01738 pvt->immediate = pri->ch_cfg.immediate;
01739 pvt->priexclusive = pri->ch_cfg.priexclusive;
01740 pvt->priindication_oob = pri->ch_cfg.priindication_oob;
01741 pvt->use_callerid = pri->ch_cfg.use_callerid;
01742 pvt->use_callingpres = pri->ch_cfg.use_callingpres;
01743 ast_copy_string(pvt->context, pri->ch_cfg.context, sizeof(pvt->context));
01744 ast_copy_string(pvt->mohinterpret, pri->ch_cfg.mohinterpret, sizeof(pvt->mohinterpret));
01745
01746 if (pri->calls->init_config) {
01747 pri->calls->init_config(pvt->chan_pvt, pri);
01748 }
01749 }
01750 #endif
01751
01752
01753
01754
01755
01756
01757
01758
01759
01760
01761
01762
01763
01764 static int pri_find_empty_chan(struct sig_pri_span *pri, int backwards)
01765 {
01766 int x;
01767 if (backwards)
01768 x = pri->numchans;
01769 else
01770 x = 0;
01771 for (;;) {
01772 if (backwards && (x < 0))
01773 break;
01774 if (!backwards && (x >= pri->numchans))
01775 break;
01776 if (pri->pvts[x]
01777 && !pri->pvts[x]->no_b_channel
01778 && sig_pri_is_chan_available(pri->pvts[x])) {
01779 ast_debug(1, "Found empty available channel %d/%d\n",
01780 pri->pvts[x]->logicalspan, pri->pvts[x]->prioffset);
01781 return x;
01782 }
01783 if (backwards)
01784 x--;
01785 else
01786 x++;
01787 }
01788 return -1;
01789 }
01790
01791 #if defined(HAVE_PRI_CALL_HOLD)
01792
01793
01794
01795
01796
01797
01798
01799
01800
01801
01802
01803
01804 static int pri_find_empty_nobch(struct sig_pri_span *pri)
01805 {
01806 int idx;
01807
01808 for (idx = 0; idx < pri->numchans; ++idx) {
01809 if (pri->pvts[idx]
01810 && pri->pvts[idx]->no_b_channel
01811 && sig_pri_is_chan_available(pri->pvts[idx])) {
01812 ast_debug(1, "Found empty available no B channel interface\n");
01813 return idx;
01814 }
01815 }
01816
01817
01818 if (pri->calls->new_nobch_intf) {
01819 idx = pri->calls->new_nobch_intf(pri);
01820 } else {
01821 idx = -1;
01822 }
01823 return idx;
01824 }
01825 #endif
01826
01827 static void *do_idle_thread(void *v_pvt)
01828 {
01829 struct sig_pri_chan *pvt = v_pvt;
01830 struct ast_channel *chan = pvt->owner;
01831 struct ast_frame *f;
01832 char ex[80];
01833
01834 int timeout_ms = 30000;
01835 int ms;
01836 struct timeval start;
01837
01838 ast_verb(3, "Initiating idle call on channel %s\n", chan->name);
01839 snprintf(ex, sizeof(ex), "%d/%s", pvt->channel, pvt->pri->idledial);
01840 if (ast_call(chan, ex, 0)) {
01841 ast_log(LOG_WARNING, "Idle dial failed on '%s' to '%s'\n", chan->name, ex);
01842 ast_hangup(chan);
01843 return NULL;
01844 }
01845 start = ast_tvnow();
01846 while ((ms = ast_remaining_ms(start, timeout_ms))) {
01847 if (ast_waitfor(chan, ms) <= 0) {
01848 break;
01849 }
01850
01851 f = ast_read(chan);
01852 if (!f) {
01853
01854 break;
01855 }
01856 if (f->frametype == AST_FRAME_CONTROL) {
01857 switch (f->subclass.integer) {
01858 case AST_CONTROL_ANSWER:
01859
01860 ast_copy_string(chan->exten, pvt->pri->idleext, sizeof(chan->exten));
01861 ast_copy_string(chan->context, pvt->pri->idlecontext, sizeof(chan->context));
01862 chan->priority = 1;
01863 ast_verb(4, "Idle channel '%s' answered, sending to %s@%s\n", chan->name, chan->exten, chan->context);
01864 ast_pbx_run(chan);
01865
01866 return NULL;
01867 case AST_CONTROL_BUSY:
01868 ast_verb(4, "Idle channel '%s' busy, waiting...\n", chan->name);
01869 break;
01870 case AST_CONTROL_CONGESTION:
01871 ast_verb(4, "Idle channel '%s' congested, waiting...\n", chan->name);
01872 break;
01873 };
01874 }
01875 ast_frfree(f);
01876 }
01877
01878 ast_hangup(chan);
01879 return NULL;
01880 }
01881
01882 static void *pri_ss_thread(void *data)
01883 {
01884 struct sig_pri_chan *p = data;
01885 struct ast_channel *chan = p->owner;
01886 char exten[AST_MAX_EXTENSION];
01887 int res;
01888 int len;
01889 int timeout;
01890
01891 if (!chan) {
01892
01893 return NULL;
01894 }
01895
01896
01897
01898
01899
01900 if (!chan->tech_pvt) {
01901 ast_log(LOG_WARNING, "Channel became a zombie before simple switch could be started (%s)\n", chan->name);
01902 ast_hangup(chan);
01903 return NULL;
01904 }
01905
01906 ast_verb(3, "Starting simple switch on '%s'\n", chan->name);
01907
01908 sig_pri_dsp_reset_and_flush_digits(p);
01909
01910
01911 ast_copy_string(exten, p->exten, sizeof(exten));
01912 len = strlen(exten);
01913 res = 0;
01914 while ((len < AST_MAX_EXTENSION-1) && ast_matchmore_extension(chan, chan->context, exten, 1, p->cid_num)) {
01915 if (len && !ast_ignore_pattern(chan->context, exten))
01916 sig_pri_play_tone(p, -1);
01917 else
01918 sig_pri_play_tone(p, SIG_PRI_TONE_DIALTONE);
01919 if (ast_exists_extension(chan, chan->context, exten, 1, p->cid_num))
01920 timeout = pri_matchdigittimeout;
01921 else
01922 timeout = pri_gendigittimeout;
01923 res = ast_waitfordigit(chan, timeout);
01924 if (res < 0) {
01925 ast_log(LOG_DEBUG, "waitfordigit returned < 0...\n");
01926 ast_hangup(chan);
01927 return NULL;
01928 } else if (res) {
01929 exten[len++] = res;
01930 exten[len] = '\0';
01931 } else
01932 break;
01933 }
01934
01935 if (ast_strlen_zero(exten)) {
01936 ast_verb(3, "Going to extension s|1 because of empty extension received on overlap call\n");
01937 exten[0] = 's';
01938 exten[1] = '\0';
01939 } else {
01940 ast_free(chan->dialed.number.str);
01941 chan->dialed.number.str = ast_strdup(exten);
01942
01943 if (p->pri->append_msn_to_user_tag && p->pri->nodetype != PRI_NETWORK) {
01944
01945
01946
01947
01948 snprintf(p->user_tag, sizeof(p->user_tag), "%s_%s", p->pri->initial_user_tag,
01949 exten);
01950 ast_free(chan->caller.id.tag);
01951 chan->caller.id.tag = ast_strdup(p->user_tag);
01952 }
01953 }
01954 sig_pri_play_tone(p, -1);
01955 if (ast_exists_extension(chan, chan->context, exten, 1, p->cid_num)) {
01956
01957 ast_copy_string(chan->exten, exten, sizeof(chan->exten));
01958 sig_pri_dsp_reset_and_flush_digits(p);
01959 #if defined(ISSUE_16789)
01960
01961
01962
01963
01964
01965
01966
01967
01968
01969
01970
01971
01972 if ((p->pri->overlapdial & DAHDI_OVERLAPDIAL_INCOMING)
01973 && !ast_matchmore_extension(chan, chan->context, exten, 1, p->cid_num)) {
01974 sig_pri_lock_private(p);
01975 if (p->pri->pri) {
01976 pri_grab(p, p->pri);
01977 if (p->call_level < SIG_PRI_CALL_LEVEL_PROCEEDING) {
01978 p->call_level = SIG_PRI_CALL_LEVEL_PROCEEDING;
01979 }
01980 pri_proceeding(p->pri->pri, p->call, PVT_TO_CHANNEL(p), 0);
01981 pri_rel(p->pri);
01982 }
01983 sig_pri_unlock_private(p);
01984 }
01985 #endif
01986
01987 sig_pri_set_echocanceller(p, 1);
01988 ast_setstate(chan, AST_STATE_RING);
01989 res = ast_pbx_run(chan);
01990 if (res) {
01991 ast_log(LOG_WARNING, "PBX exited non-zero!\n");
01992 }
01993 } else {
01994 ast_log(LOG_DEBUG, "No such possible extension '%s' in context '%s'\n", exten, chan->context);
01995 chan->hangupcause = AST_CAUSE_UNALLOCATED;
01996 ast_hangup(chan);
01997 p->exten[0] = '\0';
01998
01999 p->call = NULL;
02000 ast_mutex_lock(&p->pri->lock);
02001 sig_pri_span_devstate_changed(p->pri);
02002 ast_mutex_unlock(&p->pri->lock);
02003 }
02004 return NULL;
02005 }
02006
02007 void pri_event_alarm(struct sig_pri_span *pri, int index, int before_start_pri)
02008 {
02009 pri->dchanavail[index] &= ~(DCHAN_NOTINALARM | DCHAN_UP);
02010 if (!before_start_pri) {
02011 pri_find_dchan(pri);
02012 }
02013 }
02014
02015 void pri_event_noalarm(struct sig_pri_span *pri, int index, int before_start_pri)
02016 {
02017 pri->dchanavail[index] |= DCHAN_NOTINALARM;
02018 if (!before_start_pri)
02019 pri_restart(pri->dchans[index]);
02020 }
02021
02022
02023
02024
02025
02026
02027
02028
02029
02030
02031
02032
02033
02034
02035 static void sig_pri_party_name_convert(struct ast_party_name *ast_name, const struct pri_party_name *pri_name)
02036 {
02037 ast_name->str = ast_strdup(pri_name->str);
02038 ast_name->char_set = pri_to_ast_char_set(pri_name->char_set);
02039 ast_name->presentation = pri_to_ast_presentation(pri_name->presentation);
02040 ast_name->valid = 1;
02041 }
02042
02043
02044
02045
02046
02047
02048
02049
02050
02051
02052
02053
02054
02055
02056
02057 static void sig_pri_party_number_convert(struct ast_party_number *ast_number, const struct pri_party_number *pri_number, struct sig_pri_span *pri)
02058 {
02059 char number[AST_MAX_EXTENSION];
02060
02061 apply_plan_to_existing_number(number, sizeof(number), pri, pri_number->str,
02062 pri_number->plan);
02063 ast_number->str = ast_strdup(number);
02064 ast_number->plan = pri_number->plan;
02065 ast_number->presentation = pri_to_ast_presentation(pri_number->presentation);
02066 ast_number->valid = 1;
02067 }
02068
02069
02070
02071
02072
02073
02074
02075
02076
02077
02078
02079
02080
02081
02082
02083 static void sig_pri_party_id_convert(struct ast_party_id *ast_id, const struct pri_party_id *pri_id, struct sig_pri_span *pri)
02084 {
02085 if (pri_id->name.valid) {
02086 sig_pri_party_name_convert(&ast_id->name, &pri_id->name);
02087 }
02088 if (pri_id->number.valid) {
02089 sig_pri_party_number_convert(&ast_id->number, &pri_id->number, pri);
02090 }
02091 #if defined(HAVE_PRI_SUBADDR)
02092 if (pri_id->subaddress.valid) {
02093 sig_pri_set_subaddress(&ast_id->subaddress, &pri_id->subaddress);
02094 }
02095 #endif
02096 }
02097
02098
02099
02100
02101
02102
02103
02104
02105
02106
02107
02108
02109
02110
02111
02112
02113 static void sig_pri_redirecting_convert(struct ast_party_redirecting *ast_redirecting,
02114 const struct pri_party_redirecting *pri_redirecting,
02115 const struct ast_party_redirecting *ast_guide,
02116 struct sig_pri_span *pri)
02117 {
02118 ast_party_redirecting_set_init(ast_redirecting, ast_guide);
02119
02120 sig_pri_party_id_convert(&ast_redirecting->from, &pri_redirecting->from, pri);
02121 sig_pri_party_id_convert(&ast_redirecting->to, &pri_redirecting->to, pri);
02122 ast_redirecting->count = pri_redirecting->count;
02123 ast_redirecting->reason = pri_to_ast_reason(pri_redirecting->reason);
02124 }
02125
02126
02127
02128
02129
02130
02131
02132
02133
02134
02135
02136
02137 static int sig_pri_msn_match(const char *msn_patterns, const char *exten)
02138 {
02139 char *pattern;
02140 char *msn_list;
02141 char *list_tail;
02142
02143 msn_list = ast_strdupa(msn_patterns);
02144
02145 list_tail = NULL;
02146 pattern = strtok_r(msn_list, ",", &list_tail);
02147 while (pattern) {
02148 pattern = ast_strip(pattern);
02149 if (!ast_strlen_zero(pattern) && ast_extension_match(pattern, exten)) {
02150
02151 return 1;
02152 }
02153 pattern = strtok_r(NULL, ",", &list_tail);
02154 }
02155
02156 return 0;
02157 }
02158
02159 #if defined(HAVE_PRI_MCID)
02160
02161
02162
02163
02164
02165
02166
02167
02168
02169
02170
02171 static void sig_pri_event_party_id(struct ast_str **msg, const char *prefix, struct ast_party_id *party)
02172 {
02173 int pres;
02174
02175
02176 pres = ast_party_id_presentation(party);
02177 ast_str_append(msg, 0, "%sPres: %d (%s)\r\n", prefix, pres,
02178 ast_describe_caller_presentation(pres));
02179
02180
02181 ast_str_append(msg, 0, "%sNumValid: %d\r\n", prefix,
02182 (unsigned) party->number.valid);
02183 ast_str_append(msg, 0, "%sNum: %s\r\n", prefix,
02184 S_COR(party->number.valid, party->number.str, ""));
02185 ast_str_append(msg, 0, "%ston: %d\r\n", prefix, party->number.plan);
02186 if (party->number.valid) {
02187 ast_str_append(msg, 0, "%sNumPlan: %d\r\n", prefix, party->number.plan);
02188 ast_str_append(msg, 0, "%sNumPres: %d (%s)\r\n", prefix,
02189 party->number.presentation,
02190 ast_describe_caller_presentation(party->number.presentation));
02191 }
02192
02193
02194 ast_str_append(msg, 0, "%sNameValid: %d\r\n", prefix,
02195 (unsigned) party->name.valid);
02196 ast_str_append(msg, 0, "%sName: %s\r\n", prefix,
02197 S_COR(party->name.valid, party->name.str, ""));
02198 if (party->name.valid) {
02199 ast_str_append(msg, 0, "%sNameCharSet: %s\r\n", prefix,
02200 ast_party_name_charset_describe(party->name.char_set));
02201 ast_str_append(msg, 0, "%sNamePres: %d (%s)\r\n", prefix,
02202 party->name.presentation,
02203 ast_describe_caller_presentation(party->name.presentation));
02204 }
02205
02206 #if defined(HAVE_PRI_SUBADDR)
02207
02208 if (party->subaddress.valid) {
02209 static const char subaddress[] = "Subaddr";
02210
02211 ast_str_append(msg, 0, "%s%s: %s\r\n", prefix, subaddress,
02212 S_OR(party->subaddress.str, ""));
02213 ast_str_append(msg, 0, "%s%sType: %d\r\n", prefix, subaddress,
02214 party->subaddress.type);
02215 ast_str_append(msg, 0, "%s%sOdd: %d\r\n", prefix, subaddress,
02216 party->subaddress.odd_even_indicator);
02217 }
02218 #endif
02219 }
02220 #endif
02221
02222 #if defined(HAVE_PRI_MCID)
02223
02224
02225
02226
02227
02228
02229
02230
02231
02232
02233
02234
02235
02236
02237
02238 static void sig_pri_mcid_event(struct sig_pri_span *pri, const struct pri_subcmd_mcid_req *mcid, struct ast_channel *owner)
02239 {
02240 struct ast_channel *chans[1];
02241 struct ast_str *msg;
02242 struct ast_party_id party;
02243
02244 msg = ast_str_create(4096);
02245 if (!msg) {
02246 return;
02247 }
02248
02249 if (owner) {
02250
02251 ast_str_append(&msg, 0, "Channel: %s\r\n", owner->name);
02252 ast_str_append(&msg, 0, "UniqueID: %s\r\n", owner->uniqueid);
02253
02254 sig_pri_event_party_id(&msg, "CallerID", &owner->connected.id);
02255 } else {
02256
02257
02258
02259
02260 ast_party_id_init(&party);
02261 sig_pri_party_id_convert(&party, &mcid->originator, pri);
02262 sig_pri_event_party_id(&msg, "CallerID", &party);
02263 ast_party_id_free(&party);
02264 }
02265
02266
02267 ast_party_id_init(&party);
02268 sig_pri_party_id_convert(&party, &mcid->answerer, pri);
02269 sig_pri_event_party_id(&msg, "ConnectedID", &party);
02270 ast_party_id_free(&party);
02271
02272 chans[0] = owner;
02273 ast_manager_event_multichan(EVENT_FLAG_CALL, "MCID", owner ? 1 : 0, chans, "%s",
02274 ast_str_buffer(msg));
02275 ast_free(msg);
02276 }
02277 #endif
02278
02279 #if defined(HAVE_PRI_TRANSFER)
02280 struct xfer_rsp_data {
02281 struct sig_pri_span *pri;
02282
02283 q931_call *call;
02284
02285 int invoke_id;
02286 };
02287 #endif
02288
02289 #if defined(HAVE_PRI_TRANSFER)
02290
02291
02292
02293
02294
02295
02296
02297
02298
02299
02300 static void sig_pri_transfer_rsp(void *data, int is_successful)
02301 {
02302 struct xfer_rsp_data *rsp = data;
02303
02304 pri_transfer_rsp(rsp->pri->pri, rsp->call, rsp->invoke_id, is_successful);
02305 }
02306 #endif
02307
02308 #if defined(HAVE_PRI_CALL_HOLD) || defined(HAVE_PRI_TRANSFER)
02309
02310
02311
02312
02313
02314
02315
02316
02317
02318 typedef void (*xfer_rsp_callback)(void *data, int is_successful);
02319 #endif
02320
02321 #if defined(HAVE_PRI_CALL_HOLD) || defined(HAVE_PRI_TRANSFER)
02322
02323
02324
02325
02326
02327
02328
02329
02330
02331
02332
02333
02334
02335
02336
02337
02338
02339
02340 static int sig_pri_attempt_transfer(struct sig_pri_span *pri, q931_call *call_1_pri, int call_1_held, q931_call *call_2_pri, int call_2_held, xfer_rsp_callback rsp_callback, void *data)
02341 {
02342 struct attempt_xfer_call {
02343 q931_call *pri;
02344 struct ast_channel *ast;
02345 int held;
02346 int chanpos;
02347 };
02348 int retval;
02349 struct ast_channel *transferee;
02350 struct attempt_xfer_call *call_1;
02351 struct attempt_xfer_call *call_2;
02352 struct attempt_xfer_call *swap_call;
02353 struct attempt_xfer_call c1;
02354 struct attempt_xfer_call c2;
02355
02356 c1.pri = call_1_pri;
02357 c1.held = call_1_held;
02358 call_1 = &c1;
02359
02360 c2.pri = call_2_pri;
02361 c2.held = call_2_held;
02362 call_2 = &c2;
02363
02364 call_1->chanpos = pri_find_principle_by_call(pri, call_1->pri);
02365 call_2->chanpos = pri_find_principle_by_call(pri, call_2->pri);
02366 if (call_1->chanpos < 0 || call_2->chanpos < 0) {
02367
02368 if (rsp_callback) {
02369
02370 rsp_callback(data, 0);
02371 }
02372 return -1;
02373 }
02374
02375
02376 if (!call_1->held && call_2->held) {
02377
02378
02379
02380
02381 swap_call = call_1;
02382 call_1 = call_2;
02383 call_2 = swap_call;
02384 }
02385
02386
02387 sig_pri_lock_private(pri->pvts[call_1->chanpos]);
02388 sig_pri_lock_owner(pri, call_1->chanpos);
02389 sig_pri_lock_private(pri->pvts[call_2->chanpos]);
02390 sig_pri_lock_owner(pri, call_2->chanpos);
02391
02392 call_1->ast = pri->pvts[call_1->chanpos]->owner;
02393 call_2->ast = pri->pvts[call_2->chanpos]->owner;
02394 if (!call_1->ast || !call_2->ast) {
02395
02396 if (call_1->ast) {
02397 ast_channel_unlock(call_1->ast);
02398 }
02399 if (call_2->ast) {
02400 ast_channel_unlock(call_2->ast);
02401 }
02402 sig_pri_unlock_private(pri->pvts[call_1->chanpos]);
02403 sig_pri_unlock_private(pri->pvts[call_2->chanpos]);
02404 if (rsp_callback) {
02405
02406 rsp_callback(data, 0);
02407 }
02408 return -1;
02409 }
02410
02411 for (;;) {
02412 transferee = ast_bridged_channel(call_1->ast);
02413 if (transferee) {
02414 break;
02415 }
02416
02417
02418 swap_call = call_1;
02419 call_1 = call_2;
02420 call_2 = swap_call;
02421
02422 transferee = ast_bridged_channel(call_1->ast);
02423 if (transferee) {
02424 break;
02425 }
02426
02427
02428 ast_channel_unlock(call_1->ast);
02429 ast_channel_unlock(call_2->ast);
02430 sig_pri_unlock_private(pri->pvts[call_1->chanpos]);
02431 sig_pri_unlock_private(pri->pvts[call_2->chanpos]);
02432
02433 if (rsp_callback) {
02434
02435 rsp_callback(data, 0);
02436 }
02437 return -1;
02438 }
02439
02440 ast_verb(3, "TRANSFERRING %s to %s\n", call_1->ast->name, call_2->ast->name);
02441
02442
02443
02444
02445
02446
02447
02448
02449
02450
02451
02452
02453 ast_mutex_unlock(&pri->lock);
02454 retval = ast_channel_transfer_masquerade(
02455 call_2->ast,
02456 &call_2->ast->connected,
02457 call_2->held,
02458 transferee,
02459 &call_1->ast->connected,
02460 call_1->held);
02461
02462
02463 ast_mutex_lock(&pri->lock);
02464
02465 ast_channel_unlock(call_1->ast);
02466 ast_channel_unlock(call_2->ast);
02467 sig_pri_unlock_private(pri->pvts[call_1->chanpos]);
02468 sig_pri_unlock_private(pri->pvts[call_2->chanpos]);
02469
02470 if (rsp_callback) {
02471
02472
02473
02474
02475
02476
02477
02478 rsp_callback(data, retval ? 0 : 1);
02479 }
02480 return retval;
02481 }
02482 #endif
02483
02484 #if defined(HAVE_PRI_CCSS)
02485
02486
02487
02488
02489
02490
02491
02492
02493
02494
02495
02496 static int sig_pri_cc_agent_cmp_cc_id(void *obj, void *arg, int flags)
02497 {
02498 struct ast_cc_agent *agent_1 = obj;
02499 struct sig_pri_cc_agent_prv *agent_prv_1 = agent_1->private_data;
02500 struct sig_pri_cc_agent_prv *agent_prv_2 = arg;
02501
02502 return (agent_prv_1 && agent_prv_1->pri == agent_prv_2->pri
02503 && agent_prv_1->cc_id == agent_prv_2->cc_id) ? CMP_MATCH | CMP_STOP : 0;
02504 }
02505 #endif
02506
02507 #if defined(HAVE_PRI_CCSS)
02508
02509
02510
02511
02512
02513
02514
02515
02516
02517
02518
02519
02520
02521
02522
02523
02524 static struct ast_cc_agent *sig_pri_find_cc_agent_by_cc_id(struct sig_pri_span *pri, long cc_id)
02525 {
02526 struct sig_pri_cc_agent_prv finder = {
02527 .pri = pri,
02528 .cc_id = cc_id,
02529 };
02530
02531 return ast_cc_agent_callback(0, sig_pri_cc_agent_cmp_cc_id, &finder,
02532 sig_pri_cc_type_name);
02533 }
02534 #endif
02535
02536 #if defined(HAVE_PRI_CCSS)
02537
02538
02539
02540
02541
02542
02543
02544
02545
02546
02547
02548 static int sig_pri_cc_monitor_cmp_cc_id(void *obj, void *arg, int flags)
02549 {
02550 struct sig_pri_cc_monitor_instance *monitor_1 = obj;
02551 struct sig_pri_cc_monitor_instance *monitor_2 = arg;
02552
02553 return (monitor_1->pri == monitor_2->pri
02554 && monitor_1->cc_id == monitor_2->cc_id) ? CMP_MATCH | CMP_STOP : 0;
02555 }
02556 #endif
02557
02558 #if defined(HAVE_PRI_CCSS)
02559
02560
02561
02562
02563
02564
02565
02566
02567
02568
02569
02570
02571
02572
02573
02574
02575 static struct sig_pri_cc_monitor_instance *sig_pri_find_cc_monitor_by_cc_id(struct sig_pri_span *pri, long cc_id)
02576 {
02577 struct sig_pri_cc_monitor_instance finder = {
02578 .pri = pri,
02579 .cc_id = cc_id,
02580 };
02581
02582 return ao2_callback(sig_pri_cc_monitors, 0, sig_pri_cc_monitor_cmp_cc_id, &finder);
02583 }
02584 #endif
02585
02586 #if defined(HAVE_PRI_CCSS)
02587
02588
02589
02590
02591
02592
02593
02594
02595
02596 static void sig_pri_cc_monitor_instance_destroy(void *data)
02597 {
02598 struct sig_pri_cc_monitor_instance *monitor_instance = data;
02599
02600 if (monitor_instance->cc_id != -1) {
02601 ast_mutex_lock(&monitor_instance->pri->lock);
02602 pri_cc_cancel(monitor_instance->pri->pri, monitor_instance->cc_id);
02603 ast_mutex_unlock(&monitor_instance->pri->lock);
02604 }
02605 monitor_instance->pri->calls->module_unref();
02606 }
02607 #endif
02608
02609 #if defined(HAVE_PRI_CCSS)
02610
02611
02612
02613
02614
02615
02616
02617
02618
02619
02620
02621
02622
02623
02624
02625
02626
02627
02628 static struct sig_pri_cc_monitor_instance *sig_pri_cc_monitor_instance_init(int core_id, struct sig_pri_span *pri, long cc_id, const char *device_name)
02629 {
02630 struct sig_pri_cc_monitor_instance *monitor_instance;
02631
02632 if (!pri->calls->module_ref || !pri->calls->module_unref) {
02633 return NULL;
02634 }
02635
02636 monitor_instance = ao2_alloc(sizeof(*monitor_instance) + strlen(device_name),
02637 sig_pri_cc_monitor_instance_destroy);
02638 if (!monitor_instance) {
02639 return NULL;
02640 }
02641
02642 monitor_instance->cc_id = cc_id;
02643 monitor_instance->pri = pri;
02644 monitor_instance->core_id = core_id;
02645 strcpy(monitor_instance->name, device_name);
02646
02647 pri->calls->module_ref();
02648
02649 ao2_link(sig_pri_cc_monitors, monitor_instance);
02650 return monitor_instance;
02651 }
02652 #endif
02653
02654 #if defined(HAVE_PRI_CCSS)
02655
02656
02657
02658
02659
02660
02661
02662
02663
02664
02665
02666
02667
02668
02669
02670
02671
02672 static int sig_pri_cc_available(struct sig_pri_span *pri, int chanpos, long cc_id, enum ast_cc_service_type service)
02673 {
02674 struct sig_pri_chan *pvt;
02675 struct ast_cc_config_params *cc_params;
02676 struct sig_pri_cc_monitor_instance *monitor;
02677 enum ast_cc_monitor_policies monitor_policy;
02678 int core_id;
02679 int res;
02680 char device_name[AST_CHANNEL_NAME];
02681 char dialstring[AST_CHANNEL_NAME];
02682
02683 pvt = pri->pvts[chanpos];
02684
02685 core_id = ast_cc_get_current_core_id(pvt->owner);
02686 if (core_id == -1) {
02687 return -1;
02688 }
02689
02690 cc_params = ast_channel_get_cc_config_params(pvt->owner);
02691 if (!cc_params) {
02692 return -1;
02693 }
02694
02695 res = -1;
02696 monitor_policy = ast_get_cc_monitor_policy(cc_params);
02697 switch (monitor_policy) {
02698 case AST_CC_MONITOR_NEVER:
02699
02700 break;
02701 case AST_CC_MONITOR_NATIVE:
02702 case AST_CC_MONITOR_ALWAYS:
02703
02704
02705
02706
02707 ast_channel_get_device_name(pvt->owner, device_name, sizeof(device_name));
02708 sig_pri_make_cc_dialstring(pvt, dialstring, sizeof(dialstring));
02709 monitor = sig_pri_cc_monitor_instance_init(core_id, pri, cc_id, device_name);
02710 if (!monitor) {
02711 break;
02712 }
02713 res = ast_queue_cc_frame(pvt->owner, sig_pri_cc_type_name, dialstring, service,
02714 monitor);
02715 if (res) {
02716 monitor->cc_id = -1;
02717 ao2_unlink(sig_pri_cc_monitors, monitor);
02718 ao2_ref(monitor, -1);
02719 }
02720 break;
02721 case AST_CC_MONITOR_GENERIC:
02722 ast_queue_cc_frame(pvt->owner, AST_CC_GENERIC_MONITOR_TYPE,
02723 sig_pri_get_orig_dialstring(pvt), service, NULL);
02724
02725 break;
02726 }
02727 return res;
02728 }
02729 #endif
02730
02731
02732
02733
02734
02735
02736
02737
02738
02739
02740
02741
02742
02743
02744
02745 static void sig_pri_cc_generic_check(struct sig_pri_span *pri, int chanpos, enum ast_cc_service_type service)
02746 {
02747 struct ast_channel *owner;
02748 struct ast_cc_config_params *cc_params;
02749 #if defined(HAVE_PRI_CCSS)
02750 struct ast_cc_monitor *monitor;
02751 char device_name[AST_CHANNEL_NAME];
02752 #endif
02753 enum ast_cc_monitor_policies monitor_policy;
02754 int core_id;
02755
02756 if (!pri->pvts[chanpos]->outgoing) {
02757
02758 return;
02759 }
02760
02761 sig_pri_lock_owner(pri, chanpos);
02762 owner = pri->pvts[chanpos]->owner;
02763 if (!owner) {
02764 return;
02765 }
02766 core_id = ast_cc_get_current_core_id(owner);
02767 if (core_id == -1) {
02768
02769 goto done;
02770 }
02771
02772 cc_params = ast_channel_get_cc_config_params(owner);
02773 if (!cc_params) {
02774
02775 goto done;
02776 }
02777
02778 #if defined(HAVE_PRI_CCSS)
02779 ast_channel_get_device_name(owner, device_name, sizeof(device_name));
02780 monitor = ast_cc_get_monitor_by_recall_core_id(core_id, device_name);
02781 if (monitor) {
02782
02783 ao2_ref(monitor, -1);
02784 goto done;
02785 }
02786 #endif
02787
02788 monitor_policy = ast_get_cc_monitor_policy(cc_params);
02789 switch (monitor_policy) {
02790 case AST_CC_MONITOR_NEVER:
02791
02792 break;
02793 case AST_CC_MONITOR_NATIVE:
02794 if (pri->sig == SIG_BRI_PTMP && pri->nodetype == PRI_NETWORK) {
02795
02796 ast_queue_cc_frame(owner, AST_CC_GENERIC_MONITOR_TYPE,
02797 sig_pri_get_orig_dialstring(pri->pvts[chanpos]), service, NULL);
02798 }
02799 break;
02800 case AST_CC_MONITOR_ALWAYS:
02801 if (pri->sig == SIG_BRI_PTMP && pri->nodetype != PRI_NETWORK) {
02802
02803
02804
02805
02806
02807
02808 break;
02809 }
02810
02811
02812
02813
02814 ast_queue_cc_frame(owner, AST_CC_GENERIC_MONITOR_TYPE,
02815 sig_pri_get_orig_dialstring(pri->pvts[chanpos]), service, NULL);
02816 break;
02817 case AST_CC_MONITOR_GENERIC:
02818 if (pri->sig == SIG_BRI_PTMP && pri->nodetype == PRI_NETWORK) {
02819
02820 ast_queue_cc_frame(owner, AST_CC_GENERIC_MONITOR_TYPE,
02821 sig_pri_get_orig_dialstring(pri->pvts[chanpos]), service, NULL);
02822 }
02823 break;
02824 }
02825
02826 done:
02827 ast_channel_unlock(owner);
02828 }
02829
02830 #if defined(HAVE_PRI_CCSS)
02831
02832
02833
02834
02835
02836
02837
02838
02839
02840
02841
02842 static void sig_pri_cc_link_canceled(struct sig_pri_span *pri, long cc_id, int is_agent)
02843 {
02844 if (is_agent) {
02845 struct ast_cc_agent *agent;
02846
02847 agent = sig_pri_find_cc_agent_by_cc_id(pri, cc_id);
02848 if (!agent) {
02849 return;
02850 }
02851 ast_cc_failed(agent->core_id, "%s agent got canceled by link",
02852 sig_pri_cc_type_name);
02853 ao2_ref(agent, -1);
02854 } else {
02855 struct sig_pri_cc_monitor_instance *monitor;
02856
02857 monitor = sig_pri_find_cc_monitor_by_cc_id(pri, cc_id);
02858 if (!monitor) {
02859 return;
02860 }
02861 monitor->cc_id = -1;
02862 ast_cc_monitor_failed(monitor->core_id, monitor->name,
02863 "%s monitor got canceled by link", sig_pri_cc_type_name);
02864 ao2_ref(monitor, -1);
02865 }
02866 }
02867 #endif
02868
02869 #if defined(HAVE_PRI_AOC_EVENTS)
02870
02871
02872
02873
02874
02875
02876
02877
02878
02879 static enum PRI_AOC_CHARGED_ITEM sig_pri_aoc_charged_item_to_pri(enum PRI_AOC_CHARGED_ITEM value)
02880 {
02881 switch (value) {
02882 case AST_AOC_CHARGED_ITEM_NA:
02883 return PRI_AOC_CHARGED_ITEM_NOT_AVAILABLE;
02884 case AST_AOC_CHARGED_ITEM_SPECIAL_ARRANGEMENT:
02885 return PRI_AOC_CHARGED_ITEM_SPECIAL_ARRANGEMENT;
02886 case AST_AOC_CHARGED_ITEM_BASIC_COMMUNICATION:
02887 return PRI_AOC_CHARGED_ITEM_BASIC_COMMUNICATION;
02888 case AST_AOC_CHARGED_ITEM_CALL_ATTEMPT:
02889 return PRI_AOC_CHARGED_ITEM_CALL_ATTEMPT;
02890 case AST_AOC_CHARGED_ITEM_CALL_SETUP:
02891 return PRI_AOC_CHARGED_ITEM_CALL_SETUP;
02892 case AST_AOC_CHARGED_ITEM_USER_USER_INFO:
02893 return PRI_AOC_CHARGED_ITEM_USER_USER_INFO;
02894 case AST_AOC_CHARGED_ITEM_SUPPLEMENTARY_SERVICE:
02895 return PRI_AOC_CHARGED_ITEM_SUPPLEMENTARY_SERVICE;
02896 }
02897 return PRI_AOC_CHARGED_ITEM_NOT_AVAILABLE;
02898 }
02899 #endif
02900
02901 #if defined(HAVE_PRI_AOC_EVENTS)
02902
02903
02904
02905
02906
02907
02908
02909
02910
02911 static enum ast_aoc_s_charged_item sig_pri_aoc_charged_item_to_ast(enum PRI_AOC_CHARGED_ITEM value)
02912 {
02913 switch (value) {
02914 case PRI_AOC_CHARGED_ITEM_NOT_AVAILABLE:
02915 return AST_AOC_CHARGED_ITEM_NA;
02916 case PRI_AOC_CHARGED_ITEM_SPECIAL_ARRANGEMENT:
02917 return AST_AOC_CHARGED_ITEM_SPECIAL_ARRANGEMENT;
02918 case PRI_AOC_CHARGED_ITEM_BASIC_COMMUNICATION:
02919 return AST_AOC_CHARGED_ITEM_BASIC_COMMUNICATION;
02920 case PRI_AOC_CHARGED_ITEM_CALL_ATTEMPT:
02921 return AST_AOC_CHARGED_ITEM_CALL_ATTEMPT;
02922 case PRI_AOC_CHARGED_ITEM_CALL_SETUP:
02923 return AST_AOC_CHARGED_ITEM_CALL_SETUP;
02924 case PRI_AOC_CHARGED_ITEM_USER_USER_INFO:
02925 return AST_AOC_CHARGED_ITEM_USER_USER_INFO;
02926 case PRI_AOC_CHARGED_ITEM_SUPPLEMENTARY_SERVICE:
02927 return AST_AOC_CHARGED_ITEM_SUPPLEMENTARY_SERVICE;
02928 }
02929 return AST_AOC_CHARGED_ITEM_NA;
02930 }
02931 #endif
02932
02933 #if defined(HAVE_PRI_AOC_EVENTS)
02934
02935
02936
02937
02938
02939
02940
02941 static int sig_pri_aoc_multiplier_from_ast(enum ast_aoc_currency_multiplier mult)
02942 {
02943 switch (mult) {
02944 case AST_AOC_MULT_ONETHOUSANDTH:
02945 return PRI_AOC_MULTIPLIER_THOUSANDTH;
02946 case AST_AOC_MULT_ONEHUNDREDTH:
02947 return PRI_AOC_MULTIPLIER_HUNDREDTH;
02948 case AST_AOC_MULT_ONETENTH:
02949 return PRI_AOC_MULTIPLIER_TENTH;
02950 case AST_AOC_MULT_ONE:
02951 return PRI_AOC_MULTIPLIER_ONE;
02952 case AST_AOC_MULT_TEN:
02953 return PRI_AOC_MULTIPLIER_TEN;
02954 case AST_AOC_MULT_HUNDRED:
02955 return PRI_AOC_MULTIPLIER_HUNDRED;
02956 case AST_AOC_MULT_THOUSAND:
02957 return PRI_AOC_MULTIPLIER_THOUSAND;
02958 default:
02959 return PRI_AOC_MULTIPLIER_ONE;
02960 }
02961 }
02962 #endif
02963
02964 #if defined(HAVE_PRI_AOC_EVENTS)
02965
02966
02967
02968
02969
02970
02971
02972 static int sig_pri_aoc_multiplier_from_pri(const int mult)
02973 {
02974 switch (mult) {
02975 case PRI_AOC_MULTIPLIER_THOUSANDTH:
02976 return AST_AOC_MULT_ONETHOUSANDTH;
02977 case PRI_AOC_MULTIPLIER_HUNDREDTH:
02978 return AST_AOC_MULT_ONEHUNDREDTH;
02979 case PRI_AOC_MULTIPLIER_TENTH:
02980 return AST_AOC_MULT_ONETENTH;
02981 case PRI_AOC_MULTIPLIER_ONE:
02982 return AST_AOC_MULT_ONE;
02983 case PRI_AOC_MULTIPLIER_TEN:
02984 return AST_AOC_MULT_TEN;
02985 case PRI_AOC_MULTIPLIER_HUNDRED:
02986 return AST_AOC_MULT_HUNDRED;
02987 case PRI_AOC_MULTIPLIER_THOUSAND:
02988 return AST_AOC_MULT_THOUSAND;
02989 default:
02990 return AST_AOC_MULT_ONE;
02991 }
02992 }
02993 #endif
02994
02995 #if defined(HAVE_PRI_AOC_EVENTS)
02996
02997
02998
02999
03000
03001
03002
03003
03004
03005 static enum PRI_AOC_TIME_SCALE sig_pri_aoc_scale_to_pri(enum ast_aoc_time_scale value)
03006 {
03007 switch (value) {
03008 default:
03009 case AST_AOC_TIME_SCALE_HUNDREDTH_SECOND:
03010 return PRI_AOC_TIME_SCALE_HUNDREDTH_SECOND;
03011 case AST_AOC_TIME_SCALE_TENTH_SECOND:
03012 return PRI_AOC_TIME_SCALE_TENTH_SECOND;
03013 case AST_AOC_TIME_SCALE_SECOND:
03014 return PRI_AOC_TIME_SCALE_SECOND;
03015 case AST_AOC_TIME_SCALE_TEN_SECOND:
03016 return PRI_AOC_TIME_SCALE_TEN_SECOND;
03017 case AST_AOC_TIME_SCALE_MINUTE:
03018 return PRI_AOC_TIME_SCALE_MINUTE;
03019 case AST_AOC_TIME_SCALE_HOUR:
03020 return PRI_AOC_TIME_SCALE_HOUR;
03021 case AST_AOC_TIME_SCALE_DAY:
03022 return PRI_AOC_TIME_SCALE_DAY;
03023 }
03024 }
03025 #endif
03026
03027 #if defined(HAVE_PRI_AOC_EVENTS)
03028
03029
03030
03031
03032
03033
03034
03035
03036
03037 static enum ast_aoc_time_scale sig_pri_aoc_scale_to_ast(enum PRI_AOC_TIME_SCALE value)
03038 {
03039 switch (value) {
03040 default:
03041 case PRI_AOC_TIME_SCALE_HUNDREDTH_SECOND:
03042 return AST_AOC_TIME_SCALE_HUNDREDTH_SECOND;
03043 case PRI_AOC_TIME_SCALE_TENTH_SECOND:
03044 return AST_AOC_TIME_SCALE_TENTH_SECOND;
03045 case PRI_AOC_TIME_SCALE_SECOND:
03046 return AST_AOC_TIME_SCALE_SECOND;
03047 case PRI_AOC_TIME_SCALE_TEN_SECOND:
03048 return AST_AOC_TIME_SCALE_TEN_SECOND;
03049 case PRI_AOC_TIME_SCALE_MINUTE:
03050 return AST_AOC_TIME_SCALE_MINUTE;
03051 case PRI_AOC_TIME_SCALE_HOUR:
03052 return AST_AOC_TIME_SCALE_HOUR;
03053 case PRI_AOC_TIME_SCALE_DAY:
03054 return AST_AOC_TIME_SCALE_DAY;
03055 }
03056 return AST_AOC_TIME_SCALE_HUNDREDTH_SECOND;
03057 }
03058 #endif
03059
03060 #if defined(HAVE_PRI_AOC_EVENTS)
03061
03062
03063
03064
03065
03066
03067
03068
03069
03070
03071
03072
03073
03074
03075
03076 static void sig_pri_aoc_s_from_pri(const struct pri_subcmd_aoc_s *aoc_s, struct ast_channel *owner, int passthrough)
03077 {
03078 struct ast_aoc_decoded *decoded = NULL;
03079 struct ast_aoc_encoded *encoded = NULL;
03080 size_t encoded_size = 0;
03081 int idx;
03082
03083 if (!owner || !aoc_s) {
03084 return;
03085 }
03086
03087 if (!(decoded = ast_aoc_create(AST_AOC_S, 0, 0))) {
03088 return;
03089 }
03090
03091 for (idx = 0; idx < aoc_s->num_items; ++idx) {
03092 enum ast_aoc_s_charged_item charged_item;
03093
03094 charged_item = sig_pri_aoc_charged_item_to_ast(aoc_s->item[idx].chargeable);
03095 if (charged_item == AST_AOC_CHARGED_ITEM_NA) {
03096
03097 continue;
03098 }
03099 switch (aoc_s->item[idx].rate_type) {
03100 case PRI_AOC_RATE_TYPE_DURATION:
03101 ast_aoc_s_add_rate_duration(decoded,
03102 charged_item,
03103 aoc_s->item[idx].rate.duration.amount.cost,
03104 sig_pri_aoc_multiplier_from_pri(aoc_s->item[idx].rate.duration.amount.multiplier),
03105 aoc_s->item[idx].rate.duration.currency,
03106 aoc_s->item[idx].rate.duration.time.length,
03107 sig_pri_aoc_scale_to_ast(aoc_s->item[idx].rate.duration.time.scale),
03108 aoc_s->item[idx].rate.duration.granularity.length,
03109 sig_pri_aoc_scale_to_ast(aoc_s->item[idx].rate.duration.granularity.scale),
03110 aoc_s->item[idx].rate.duration.charging_type);
03111 break;
03112 case PRI_AOC_RATE_TYPE_FLAT:
03113 ast_aoc_s_add_rate_flat(decoded,
03114 charged_item,
03115 aoc_s->item[idx].rate.flat.amount.cost,
03116 sig_pri_aoc_multiplier_from_pri(aoc_s->item[idx].rate.flat.amount.multiplier),
03117 aoc_s->item[idx].rate.flat.currency);
03118 break;
03119 case PRI_AOC_RATE_TYPE_VOLUME:
03120 ast_aoc_s_add_rate_volume(decoded,
03121 charged_item,
03122 aoc_s->item[idx].rate.volume.unit,
03123 aoc_s->item[idx].rate.volume.amount.cost,
03124 sig_pri_aoc_multiplier_from_pri(aoc_s->item[idx].rate.volume.amount.multiplier),
03125 aoc_s->item[idx].rate.volume.currency);
03126 break;
03127 case PRI_AOC_RATE_TYPE_SPECIAL_CODE:
03128 ast_aoc_s_add_rate_special_charge_code(decoded,
03129 charged_item,
03130 aoc_s->item[idx].rate.special);
03131 break;
03132 case PRI_AOC_RATE_TYPE_FREE:
03133 ast_aoc_s_add_rate_free(decoded, charged_item, 0);
03134 break;
03135 case PRI_AOC_RATE_TYPE_FREE_FROM_BEGINNING:
03136 ast_aoc_s_add_rate_free(decoded, charged_item, 1);
03137 break;
03138 default:
03139 ast_aoc_s_add_rate_na(decoded, charged_item);
03140 break;
03141 }
03142 }
03143
03144 if (passthrough && (encoded = ast_aoc_encode(decoded, &encoded_size, owner))) {
03145 ast_queue_control_data(owner, AST_CONTROL_AOC, encoded, encoded_size);
03146 }
03147
03148 ast_aoc_manager_event(decoded, owner);
03149
03150 ast_aoc_destroy_decoded(decoded);
03151 ast_aoc_destroy_encoded(encoded);
03152 }
03153 #endif
03154
03155 #if defined(HAVE_PRI_AOC_EVENTS)
03156
03157
03158
03159
03160
03161
03162
03163
03164
03165
03166
03167
03168
03169 static void sig_pri_aoc_request_from_pri(const struct pri_subcmd_aoc_request *aoc_request, struct sig_pri_chan *pvt, q931_call *call)
03170 {
03171 int request;
03172
03173 if (!aoc_request) {
03174 return;
03175 }
03176
03177 request = aoc_request->charging_request;
03178
03179 if (request & PRI_AOC_REQUEST_S) {
03180 if (pvt->pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_S) {
03181
03182
03183 pvt->aoc_s_request_invoke_id = aoc_request->invoke_id;
03184 pvt->aoc_s_request_invoke_id_valid = 1;
03185
03186 } else {
03187 pri_aoc_s_request_response_send(pvt->pri->pri,
03188 call,
03189 aoc_request->invoke_id,
03190 NULL);
03191 }
03192 }
03193
03194 if (request & PRI_AOC_REQUEST_D) {
03195 if (pvt->pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_D) {
03196 pri_aoc_de_request_response_send(pvt->pri->pri,
03197 call,
03198 PRI_AOC_REQ_RSP_CHARGING_INFO_FOLLOWS,
03199 aoc_request->invoke_id);
03200 } else {
03201 pri_aoc_de_request_response_send(pvt->pri->pri,
03202 call,
03203 PRI_AOC_REQ_RSP_ERROR_NOT_AVAILABLE,
03204 aoc_request->invoke_id);
03205 }
03206 }
03207
03208 if (request & PRI_AOC_REQUEST_E) {
03209 if (pvt->pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_E) {
03210 pri_aoc_de_request_response_send(pvt->pri->pri,
03211 call,
03212 PRI_AOC_REQ_RSP_CHARGING_INFO_FOLLOWS,
03213 aoc_request->invoke_id);
03214 } else {
03215 pri_aoc_de_request_response_send(pvt->pri->pri,
03216 call,
03217 PRI_AOC_REQ_RSP_ERROR_NOT_AVAILABLE,
03218 aoc_request->invoke_id);
03219 }
03220 }
03221 }
03222 #endif
03223
03224 #if defined(HAVE_PRI_AOC_EVENTS)
03225
03226
03227
03228
03229
03230
03231
03232
03233
03234
03235
03236
03237
03238
03239
03240 static void sig_pri_aoc_d_from_pri(const struct pri_subcmd_aoc_d *aoc_d, struct ast_channel *owner, int passthrough)
03241 {
03242 struct ast_aoc_decoded *decoded = NULL;
03243 struct ast_aoc_encoded *encoded = NULL;
03244 size_t encoded_size = 0;
03245 enum ast_aoc_charge_type type;
03246
03247 if (!owner || !aoc_d) {
03248 return;
03249 }
03250
03251 switch (aoc_d->charge) {
03252 case PRI_AOC_DE_CHARGE_CURRENCY:
03253 type = AST_AOC_CHARGE_CURRENCY;
03254 break;
03255 case PRI_AOC_DE_CHARGE_UNITS:
03256 type = AST_AOC_CHARGE_UNIT;
03257 break;
03258 case PRI_AOC_DE_CHARGE_FREE:
03259 type = AST_AOC_CHARGE_FREE;
03260 break;
03261 default:
03262 type = AST_AOC_CHARGE_NA;
03263 break;
03264 }
03265
03266 if (!(decoded = ast_aoc_create(AST_AOC_D, type, 0))) {
03267 return;
03268 }
03269
03270 switch (aoc_d->billing_accumulation) {
03271 default:
03272 ast_debug(1, "AOC-D billing accumulation has unknown value: %d\n",
03273 aoc_d->billing_accumulation);
03274
03275 case 0:
03276 ast_aoc_set_total_type(decoded, AST_AOC_SUBTOTAL);
03277 break;
03278 case 1:
03279 ast_aoc_set_total_type(decoded, AST_AOC_TOTAL);
03280 break;
03281 }
03282
03283 switch (aoc_d->billing_id) {
03284 case PRI_AOC_D_BILLING_ID_NORMAL:
03285 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_NORMAL);
03286 break;
03287 case PRI_AOC_D_BILLING_ID_REVERSE:
03288 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_REVERSE_CHARGE);
03289 break;
03290 case PRI_AOC_D_BILLING_ID_CREDIT_CARD:
03291 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_CREDIT_CARD);
03292 break;
03293 case PRI_AOC_D_BILLING_ID_NOT_AVAILABLE:
03294 default:
03295 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_NA);
03296 break;
03297 }
03298
03299 switch (aoc_d->charge) {
03300 case PRI_AOC_DE_CHARGE_CURRENCY:
03301 ast_aoc_set_currency_info(decoded,
03302 aoc_d->recorded.money.amount.cost,
03303 sig_pri_aoc_multiplier_from_pri(aoc_d->recorded.money.amount.multiplier),
03304 aoc_d->recorded.money.currency);
03305 break;
03306 case PRI_AOC_DE_CHARGE_UNITS:
03307 {
03308 int i;
03309 for (i = 0; i < aoc_d->recorded.unit.num_items; ++i) {
03310
03311 ast_aoc_add_unit_entry(decoded,
03312 (aoc_d->recorded.unit.item[i].number >= 0 ? 1 : 0),
03313 aoc_d->recorded.unit.item[i].number,
03314 (aoc_d->recorded.unit.item[i].type >= 0 ? 1 : 0),
03315 aoc_d->recorded.unit.item[i].type);
03316 }
03317 }
03318 break;
03319 }
03320
03321 if (passthrough && (encoded = ast_aoc_encode(decoded, &encoded_size, owner))) {
03322 ast_queue_control_data(owner, AST_CONTROL_AOC, encoded, encoded_size);
03323 }
03324
03325 ast_aoc_manager_event(decoded, owner);
03326
03327 ast_aoc_destroy_decoded(decoded);
03328 ast_aoc_destroy_encoded(encoded);
03329 }
03330 #endif
03331
03332 #if defined(HAVE_PRI_AOC_EVENTS)
03333
03334
03335
03336
03337
03338
03339
03340
03341
03342
03343
03344
03345
03346
03347
03348
03349 static void sig_pri_aoc_e_from_pri(const struct pri_subcmd_aoc_e *aoc_e, struct ast_channel *owner, int passthrough)
03350 {
03351 struct ast_aoc_decoded *decoded = NULL;
03352 struct ast_aoc_encoded *encoded = NULL;
03353 size_t encoded_size = 0;
03354 enum ast_aoc_charge_type type;
03355
03356 if (!aoc_e) {
03357 return;
03358 }
03359
03360 switch (aoc_e->charge) {
03361 case PRI_AOC_DE_CHARGE_CURRENCY:
03362 type = AST_AOC_CHARGE_CURRENCY;
03363 break;
03364 case PRI_AOC_DE_CHARGE_UNITS:
03365 type = AST_AOC_CHARGE_UNIT;
03366 break;
03367 case PRI_AOC_DE_CHARGE_FREE:
03368 type = AST_AOC_CHARGE_FREE;
03369 break;
03370 default:
03371 type = AST_AOC_CHARGE_NA;
03372 break;
03373 }
03374
03375 if (!(decoded = ast_aoc_create(AST_AOC_E, type, 0))) {
03376 return;
03377 }
03378
03379 switch (aoc_e->associated.charging_type) {
03380 case PRI_AOC_E_CHARGING_ASSOCIATION_NUMBER:
03381 if (!aoc_e->associated.charge.number.valid) {
03382 break;
03383 }
03384 ast_aoc_set_association_number(decoded, aoc_e->associated.charge.number.str, aoc_e->associated.charge.number.plan);
03385 break;
03386 case PRI_AOC_E_CHARGING_ASSOCIATION_ID:
03387 ast_aoc_set_association_id(decoded, aoc_e->associated.charge.id);
03388 break;
03389 default:
03390 break;
03391 }
03392
03393 switch (aoc_e->billing_id) {
03394 case PRI_AOC_E_BILLING_ID_NORMAL:
03395 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_NORMAL);
03396 break;
03397 case PRI_AOC_E_BILLING_ID_REVERSE:
03398 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_REVERSE_CHARGE);
03399 break;
03400 case PRI_AOC_E_BILLING_ID_CREDIT_CARD:
03401 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_CREDIT_CARD);
03402 break;
03403 case PRI_AOC_E_BILLING_ID_CALL_FORWARDING_UNCONDITIONAL:
03404 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_CALL_FWD_UNCONDITIONAL);
03405 break;
03406 case PRI_AOC_E_BILLING_ID_CALL_FORWARDING_BUSY:
03407 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_CALL_FWD_BUSY);
03408 break;
03409 case PRI_AOC_E_BILLING_ID_CALL_FORWARDING_NO_REPLY:
03410 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_CALL_FWD_NO_REPLY);
03411 break;
03412 case PRI_AOC_E_BILLING_ID_CALL_DEFLECTION:
03413 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_CALL_DEFLECTION);
03414 break;
03415 case PRI_AOC_E_BILLING_ID_CALL_TRANSFER:
03416 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_CALL_TRANSFER);
03417 break;
03418 case PRI_AOC_E_BILLING_ID_NOT_AVAILABLE:
03419 default:
03420 ast_aoc_set_billing_id(decoded, AST_AOC_BILLING_NA);
03421 break;
03422 }
03423
03424 switch (aoc_e->charge) {
03425 case PRI_AOC_DE_CHARGE_CURRENCY:
03426 ast_aoc_set_currency_info(decoded,
03427 aoc_e->recorded.money.amount.cost,
03428 sig_pri_aoc_multiplier_from_pri(aoc_e->recorded.money.amount.multiplier),
03429 aoc_e->recorded.money.currency);
03430 break;
03431 case PRI_AOC_DE_CHARGE_UNITS:
03432 {
03433 int i;
03434 for (i = 0; i < aoc_e->recorded.unit.num_items; ++i) {
03435
03436 ast_aoc_add_unit_entry(decoded,
03437 (aoc_e->recorded.unit.item[i].number >= 0 ? 1 : 0),
03438 aoc_e->recorded.unit.item[i].number,
03439 (aoc_e->recorded.unit.item[i].type >= 0 ? 1 : 0),
03440 aoc_e->recorded.unit.item[i].type);
03441 }
03442 }
03443 }
03444
03445 if (passthrough && owner && (encoded = ast_aoc_encode(decoded, &encoded_size, owner))) {
03446 ast_queue_control_data(owner, AST_CONTROL_AOC, encoded, encoded_size);
03447 }
03448
03449 ast_aoc_manager_event(decoded, owner);
03450
03451 ast_aoc_destroy_decoded(decoded);
03452 ast_aoc_destroy_encoded(encoded);
03453 }
03454 #endif
03455
03456 #if defined(HAVE_PRI_AOC_EVENTS)
03457
03458
03459
03460
03461
03462
03463
03464
03465
03466
03467
03468 static void sig_pri_aoc_s_from_ast(struct sig_pri_chan *pvt, struct ast_aoc_decoded *decoded)
03469 {
03470 struct pri_subcmd_aoc_s aoc_s = { 0, };
03471 const struct ast_aoc_s_entry *entry;
03472 int idx;
03473
03474 for (idx = 0; idx < ast_aoc_s_get_count(decoded); idx++) {
03475 if (!(entry = ast_aoc_s_get_rate_info(decoded, idx))) {
03476 break;
03477 }
03478
03479 aoc_s.item[idx].chargeable = sig_pri_aoc_charged_item_to_pri(entry->charged_item);
03480
03481 switch (entry->rate_type) {
03482 case AST_AOC_RATE_TYPE_DURATION:
03483 aoc_s.item[idx].rate_type = PRI_AOC_RATE_TYPE_DURATION;
03484 aoc_s.item[idx].rate.duration.amount.cost = entry->rate.duration.amount;
03485 aoc_s.item[idx].rate.duration.amount.multiplier =
03486 sig_pri_aoc_multiplier_from_ast(entry->rate.duration.multiplier);
03487 aoc_s.item[idx].rate.duration.time.length = entry->rate.duration.time;
03488 aoc_s.item[idx].rate.duration.time.scale =
03489 sig_pri_aoc_scale_to_pri(entry->rate.duration.time_scale);
03490 aoc_s.item[idx].rate.duration.granularity.length = entry->rate.duration.granularity_time;
03491 aoc_s.item[idx].rate.duration.granularity.scale =
03492 sig_pri_aoc_scale_to_pri(entry->rate.duration.granularity_time_scale);
03493 aoc_s.item[idx].rate.duration.charging_type = entry->rate.duration.charging_type;
03494
03495 if (!ast_strlen_zero(entry->rate.duration.currency_name)) {
03496 ast_copy_string(aoc_s.item[idx].rate.duration.currency,
03497 entry->rate.duration.currency_name,
03498 sizeof(aoc_s.item[idx].rate.duration.currency));
03499 }
03500 break;
03501 case AST_AOC_RATE_TYPE_FLAT:
03502 aoc_s.item[idx].rate_type = PRI_AOC_RATE_TYPE_FLAT;
03503 aoc_s.item[idx].rate.flat.amount.cost = entry->rate.flat.amount;
03504 aoc_s.item[idx].rate.flat.amount.multiplier =
03505 sig_pri_aoc_multiplier_from_ast(entry->rate.flat.multiplier);
03506
03507 if (!ast_strlen_zero(entry->rate.flat.currency_name)) {
03508 ast_copy_string(aoc_s.item[idx].rate.flat.currency,
03509 entry->rate.flat.currency_name,
03510 sizeof(aoc_s.item[idx].rate.flat.currency));
03511 }
03512 break;
03513 case AST_AOC_RATE_TYPE_VOLUME:
03514 aoc_s.item[idx].rate_type = PRI_AOC_RATE_TYPE_VOLUME;
03515 aoc_s.item[idx].rate.volume.unit = entry->rate.volume.volume_unit;
03516 aoc_s.item[idx].rate.volume.amount.cost = entry->rate.volume.amount;
03517 aoc_s.item[idx].rate.volume.amount.multiplier =
03518 sig_pri_aoc_multiplier_from_ast(entry->rate.volume.multiplier);
03519
03520 if (!ast_strlen_zero(entry->rate.volume.currency_name)) {
03521 ast_copy_string(aoc_s.item[idx].rate.volume.currency,
03522 entry->rate.volume.currency_name,
03523 sizeof(aoc_s.item[idx].rate.volume.currency));
03524 }
03525 break;
03526 case AST_AOC_RATE_TYPE_SPECIAL_CODE:
03527 aoc_s.item[idx].rate_type = PRI_AOC_RATE_TYPE_SPECIAL_CODE;
03528 aoc_s.item[idx].rate.special = entry->rate.special_code;
03529 break;
03530 case AST_AOC_RATE_TYPE_FREE:
03531 aoc_s.item[idx].rate_type = PRI_AOC_RATE_TYPE_FREE;
03532 break;
03533 case AST_AOC_RATE_TYPE_FREE_FROM_BEGINNING:
03534 aoc_s.item[idx].rate_type = PRI_AOC_RATE_TYPE_FREE_FROM_BEGINNING;
03535 break;
03536 default:
03537 case AST_AOC_RATE_TYPE_NA:
03538 aoc_s.item[idx].rate_type = PRI_AOC_RATE_TYPE_NOT_AVAILABLE;
03539 break;
03540 }
03541 }
03542 aoc_s.num_items = idx;
03543
03544
03545
03546 if (pvt->aoc_s_request_invoke_id_valid) {
03547 pri_aoc_s_request_response_send(pvt->pri->pri, pvt->call, pvt->aoc_s_request_invoke_id, &aoc_s);
03548 pvt->aoc_s_request_invoke_id_valid = 0;
03549 } else {
03550 pri_aoc_s_send(pvt->pri->pri, pvt->call, &aoc_s);
03551 }
03552 }
03553 #endif
03554
03555 #if defined(HAVE_PRI_AOC_EVENTS)
03556
03557
03558
03559
03560
03561
03562
03563
03564
03565
03566
03567 static void sig_pri_aoc_d_from_ast(struct sig_pri_chan *pvt, struct ast_aoc_decoded *decoded)
03568 {
03569 struct pri_subcmd_aoc_d aoc_d = { 0, };
03570
03571 aoc_d.billing_accumulation = (ast_aoc_get_total_type(decoded) == AST_AOC_TOTAL) ? 1 : 0;
03572
03573 switch (ast_aoc_get_billing_id(decoded)) {
03574 case AST_AOC_BILLING_NORMAL:
03575 aoc_d.billing_id = PRI_AOC_D_BILLING_ID_NORMAL;
03576 break;
03577 case AST_AOC_BILLING_REVERSE_CHARGE:
03578 aoc_d.billing_id = PRI_AOC_D_BILLING_ID_REVERSE;
03579 break;
03580 case AST_AOC_BILLING_CREDIT_CARD:
03581 aoc_d.billing_id = PRI_AOC_D_BILLING_ID_CREDIT_CARD;
03582 break;
03583 case AST_AOC_BILLING_NA:
03584 default:
03585 aoc_d.billing_id = PRI_AOC_D_BILLING_ID_NOT_AVAILABLE;
03586 break;
03587 }
03588
03589 switch (ast_aoc_get_charge_type(decoded)) {
03590 case AST_AOC_CHARGE_FREE:
03591 aoc_d.charge = PRI_AOC_DE_CHARGE_FREE;
03592 break;
03593 case AST_AOC_CHARGE_CURRENCY:
03594 {
03595 const char *currency_name = ast_aoc_get_currency_name(decoded);
03596 aoc_d.charge = PRI_AOC_DE_CHARGE_CURRENCY;
03597 aoc_d.recorded.money.amount.cost = ast_aoc_get_currency_amount(decoded);
03598 aoc_d.recorded.money.amount.multiplier = sig_pri_aoc_multiplier_from_ast(ast_aoc_get_currency_multiplier(decoded));
03599 if (!ast_strlen_zero(currency_name)) {
03600 ast_copy_string(aoc_d.recorded.money.currency, currency_name, sizeof(aoc_d.recorded.money.currency));
03601 }
03602 }
03603 break;
03604 case AST_AOC_CHARGE_UNIT:
03605 {
03606 const struct ast_aoc_unit_entry *entry;
03607 int i;
03608 aoc_d.charge = PRI_AOC_DE_CHARGE_UNITS;
03609 for (i = 0; i < ast_aoc_get_unit_count(decoded); i++) {
03610 if ((entry = ast_aoc_get_unit_info(decoded, i)) && i < ARRAY_LEN(aoc_d.recorded.unit.item)) {
03611 if (entry->valid_amount) {
03612 aoc_d.recorded.unit.item[i].number = entry->amount;
03613 } else {
03614 aoc_d.recorded.unit.item[i].number = -1;
03615 }
03616 if (entry->valid_type) {
03617 aoc_d.recorded.unit.item[i].type = entry->type;
03618 } else {
03619 aoc_d.recorded.unit.item[i].type = -1;
03620 }
03621 aoc_d.recorded.unit.num_items++;
03622 } else {
03623 break;
03624 }
03625 }
03626 }
03627 break;
03628 case AST_AOC_CHARGE_NA:
03629 default:
03630 aoc_d.charge = PRI_AOC_DE_CHARGE_NOT_AVAILABLE;
03631 break;
03632 }
03633
03634 pri_aoc_d_send(pvt->pri->pri, pvt->call, &aoc_d);
03635 }
03636 #endif
03637
03638 #if defined(HAVE_PRI_AOC_EVENTS)
03639
03640
03641
03642
03643
03644
03645
03646
03647
03648
03649
03650 static void sig_pri_aoc_e_from_ast(struct sig_pri_chan *pvt, struct ast_aoc_decoded *decoded)
03651 {
03652 struct pri_subcmd_aoc_e *aoc_e = &pvt->aoc_e;
03653 const struct ast_aoc_charging_association *ca = ast_aoc_get_association_info(decoded);
03654
03655 memset(aoc_e, 0, sizeof(*aoc_e));
03656 pvt->holding_aoce = 1;
03657
03658 switch (ca->charging_type) {
03659 case AST_AOC_CHARGING_ASSOCIATION_NUMBER:
03660 aoc_e->associated.charge.number.valid = 1;
03661 ast_copy_string(aoc_e->associated.charge.number.str,
03662 ca->charge.number.number,
03663 sizeof(aoc_e->associated.charge.number.str));
03664 aoc_e->associated.charge.number.plan = ca->charge.number.plan;
03665 aoc_e->associated.charging_type = PRI_AOC_E_CHARGING_ASSOCIATION_NUMBER;
03666 break;
03667 case AST_AOC_CHARGING_ASSOCIATION_ID:
03668 aoc_e->associated.charge.id = ca->charge.id;
03669 aoc_e->associated.charging_type = PRI_AOC_E_CHARGING_ASSOCIATION_ID;
03670 break;
03671 case AST_AOC_CHARGING_ASSOCIATION_NA:
03672 default:
03673 break;
03674 }
03675
03676 switch (ast_aoc_get_billing_id(decoded)) {
03677 case AST_AOC_BILLING_NORMAL:
03678 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_NORMAL;
03679 break;
03680 case AST_AOC_BILLING_REVERSE_CHARGE:
03681 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_REVERSE;
03682 break;
03683 case AST_AOC_BILLING_CREDIT_CARD:
03684 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_CREDIT_CARD;
03685 break;
03686 case AST_AOC_BILLING_CALL_FWD_UNCONDITIONAL:
03687 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_CALL_FORWARDING_UNCONDITIONAL;
03688 break;
03689 case AST_AOC_BILLING_CALL_FWD_BUSY:
03690 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_CALL_FORWARDING_BUSY;
03691 break;
03692 case AST_AOC_BILLING_CALL_FWD_NO_REPLY:
03693 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_CALL_FORWARDING_NO_REPLY;
03694 break;
03695 case AST_AOC_BILLING_CALL_DEFLECTION:
03696 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_CALL_DEFLECTION;
03697 break;
03698 case AST_AOC_BILLING_CALL_TRANSFER:
03699 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_CALL_TRANSFER;
03700 break;
03701 case AST_AOC_BILLING_NA:
03702 default:
03703 aoc_e->billing_id = PRI_AOC_E_BILLING_ID_NOT_AVAILABLE;
03704 break;
03705 }
03706
03707 switch (ast_aoc_get_charge_type(decoded)) {
03708 case AST_AOC_CHARGE_FREE:
03709 aoc_e->charge = PRI_AOC_DE_CHARGE_FREE;
03710 break;
03711 case AST_AOC_CHARGE_CURRENCY:
03712 {
03713 const char *currency_name = ast_aoc_get_currency_name(decoded);
03714 aoc_e->charge = PRI_AOC_DE_CHARGE_CURRENCY;
03715 aoc_e->recorded.money.amount.cost = ast_aoc_get_currency_amount(decoded);
03716 aoc_e->recorded.money.amount.multiplier = sig_pri_aoc_multiplier_from_ast(ast_aoc_get_currency_multiplier(decoded));
03717 if (!ast_strlen_zero(currency_name)) {
03718 ast_copy_string(aoc_e->recorded.money.currency, currency_name, sizeof(aoc_e->recorded.money.currency));
03719 }
03720 }
03721 break;
03722 case AST_AOC_CHARGE_UNIT:
03723 {
03724 const struct ast_aoc_unit_entry *entry;
03725 int i;
03726 aoc_e->charge = PRI_AOC_DE_CHARGE_UNITS;
03727 for (i = 0; i < ast_aoc_get_unit_count(decoded); i++) {
03728 if ((entry = ast_aoc_get_unit_info(decoded, i)) && i < ARRAY_LEN(aoc_e->recorded.unit.item)) {
03729 if (entry->valid_amount) {
03730 aoc_e->recorded.unit.item[i].number = entry->amount;
03731 } else {
03732 aoc_e->recorded.unit.item[i].number = -1;
03733 }
03734 if (entry->valid_type) {
03735 aoc_e->recorded.unit.item[i].type = entry->type;
03736 } else {
03737 aoc_e->recorded.unit.item[i].type = -1;
03738 }
03739 aoc_e->recorded.unit.num_items++;
03740 }
03741 }
03742 }
03743 break;
03744 case AST_AOC_CHARGE_NA:
03745 default:
03746 aoc_e->charge = PRI_AOC_DE_CHARGE_NOT_AVAILABLE;
03747 break;
03748 }
03749 }
03750 #endif
03751
03752 #if defined(HAVE_PRI_AOC_EVENTS)
03753
03754
03755
03756
03757
03758
03759
03760
03761
03762
03763
03764
03765
03766
03767 static void sig_pri_send_aoce_termination_request(struct sig_pri_span *pri, int chanpos, unsigned int ms)
03768 {
03769 struct sig_pri_chan *pvt;
03770 struct ast_aoc_decoded *decoded = NULL;
03771 struct ast_aoc_encoded *encoded = NULL;
03772 size_t encoded_size;
03773 struct timeval whentohangup = { 0, };
03774
03775 sig_pri_lock_owner(pri, chanpos);
03776 pvt = pri->pvts[chanpos];
03777 if (!pvt->owner) {
03778 return;
03779 }
03780
03781 if (!(decoded = ast_aoc_create(AST_AOC_REQUEST, 0, AST_AOC_REQUEST_E))) {
03782 ast_softhangup_nolock(pvt->owner, AST_SOFTHANGUP_DEV);
03783 goto cleanup_termination_request;
03784 }
03785
03786 ast_aoc_set_termination_request(decoded);
03787
03788 if (!(encoded = ast_aoc_encode(decoded, &encoded_size, pvt->owner))) {
03789 ast_softhangup_nolock(pvt->owner, AST_SOFTHANGUP_DEV);
03790 goto cleanup_termination_request;
03791 }
03792
03793
03794 whentohangup.tv_usec = (ms % 1000) * 1000;
03795 whentohangup.tv_sec = ms / 1000;
03796
03797 if (ast_queue_control_data(pvt->owner, AST_CONTROL_AOC, encoded, encoded_size)) {
03798 ast_softhangup_nolock(pvt->owner, AST_SOFTHANGUP_DEV);
03799 goto cleanup_termination_request;
03800 }
03801
03802 pvt->waiting_for_aoce = 1;
03803 ast_channel_setwhentohangup_tv(pvt->owner, whentohangup);
03804 ast_log(LOG_DEBUG, "Delaying hangup on %s for aoc-e msg\n", pvt->owner->name);
03805
03806 cleanup_termination_request:
03807 ast_channel_unlock(pvt->owner);
03808 ast_aoc_destroy_decoded(decoded);
03809 ast_aoc_destroy_encoded(encoded);
03810 }
03811 #endif
03812
03813
03814
03815
03816
03817
03818
03819
03820
03821
03822 static int sig_pri_is_cis_call(int channel)
03823 {
03824 return channel != -1 && (channel & PRI_CIS_CALL);
03825 }
03826
03827
03828
03829
03830
03831
03832
03833
03834
03835
03836
03837
03838
03839
03840
03841
03842
03843
03844 static void sig_pri_handle_cis_subcmds(struct sig_pri_span *pri, int event_id,
03845 const struct pri_subcommands *subcmds, q931_call *call_rsp)
03846 {
03847 int index;
03848 #if defined(HAVE_PRI_CCSS)
03849 struct ast_cc_agent *agent;
03850 struct sig_pri_cc_agent_prv *agent_prv;
03851 struct sig_pri_cc_monitor_instance *monitor;
03852 #endif
03853
03854 if (!subcmds) {
03855 return;
03856 }
03857 for (index = 0; index < subcmds->counter_subcmd; ++index) {
03858 const struct pri_subcommand *subcmd = &subcmds->subcmd[index];
03859
03860 switch (subcmd->cmd) {
03861 #if defined(STATUS_REQUEST_PLACE_HOLDER)
03862 case PRI_SUBCMD_STATUS_REQ:
03863 case PRI_SUBCMD_STATUS_REQ_RSP:
03864
03865 break;
03866 #endif
03867 #if defined(HAVE_PRI_CCSS)
03868 case PRI_SUBCMD_CC_REQ:
03869 agent = sig_pri_find_cc_agent_by_cc_id(pri, subcmd->u.cc_request.cc_id);
03870 if (!agent) {
03871 pri_cc_cancel(pri->pri, subcmd->u.cc_request.cc_id);
03872 break;
03873 }
03874 if (!ast_cc_request_is_within_limits()) {
03875 if (pri_cc_req_rsp(pri->pri, subcmd->u.cc_request.cc_id,
03876 5)) {
03877 pri_cc_cancel(pri->pri, subcmd->u.cc_request.cc_id);
03878 }
03879 ast_cc_failed(agent->core_id, "%s agent system CC queue full",
03880 sig_pri_cc_type_name);
03881 ao2_ref(agent, -1);
03882 break;
03883 }
03884 agent_prv = agent->private_data;
03885 agent_prv->cc_request_response_pending = 1;
03886 if (ast_cc_agent_accept_request(agent->core_id,
03887 "%s caller accepted CC offer.", sig_pri_cc_type_name)) {
03888 agent_prv->cc_request_response_pending = 0;
03889 if (pri_cc_req_rsp(pri->pri, subcmd->u.cc_request.cc_id,
03890 2)) {
03891 pri_cc_cancel(pri->pri, subcmd->u.cc_request.cc_id);
03892 }
03893 ast_cc_failed(agent->core_id, "%s agent CC core request accept failed",
03894 sig_pri_cc_type_name);
03895 }
03896 ao2_ref(agent, -1);
03897 break;
03898 #endif
03899 #if defined(HAVE_PRI_CCSS)
03900 case PRI_SUBCMD_CC_REQ_RSP:
03901 monitor = sig_pri_find_cc_monitor_by_cc_id(pri,
03902 subcmd->u.cc_request_rsp.cc_id);
03903 if (!monitor) {
03904 pri_cc_cancel(pri->pri, subcmd->u.cc_request_rsp.cc_id);
03905 break;
03906 }
03907 switch (subcmd->u.cc_request_rsp.status) {
03908 case 0:
03909 ast_cc_monitor_request_acked(monitor->core_id,
03910 "%s far end accepted CC request", sig_pri_cc_type_name);
03911 break;
03912 case 1:
03913 ast_verb(2, "core_id:%d %s CC request timeout\n", monitor->core_id,
03914 sig_pri_cc_type_name);
03915 ast_cc_monitor_failed(monitor->core_id, monitor->name,
03916 "%s CC request timeout", sig_pri_cc_type_name);
03917 break;
03918 case 2:
03919 ast_verb(2, "core_id:%d %s CC request error: %s\n", monitor->core_id,
03920 sig_pri_cc_type_name,
03921 pri_facility_error2str(subcmd->u.cc_request_rsp.fail_code));
03922 ast_cc_monitor_failed(monitor->core_id, monitor->name,
03923 "%s CC request error", sig_pri_cc_type_name);
03924 break;
03925 case 3:
03926 ast_verb(2, "core_id:%d %s CC request reject: %s\n", monitor->core_id,
03927 sig_pri_cc_type_name,
03928 pri_facility_reject2str(subcmd->u.cc_request_rsp.fail_code));
03929 ast_cc_monitor_failed(monitor->core_id, monitor->name,
03930 "%s CC request reject", sig_pri_cc_type_name);
03931 break;
03932 default:
03933 ast_verb(2, "core_id:%d %s CC request unknown status %d\n",
03934 monitor->core_id, sig_pri_cc_type_name,
03935 subcmd->u.cc_request_rsp.status);
03936 ast_cc_monitor_failed(monitor->core_id, monitor->name,
03937 "%s CC request unknown status", sig_pri_cc_type_name);
03938 break;
03939 }
03940 ao2_ref(monitor, -1);
03941 break;
03942 #endif
03943 #if defined(HAVE_PRI_CCSS)
03944 case PRI_SUBCMD_CC_REMOTE_USER_FREE:
03945 monitor = sig_pri_find_cc_monitor_by_cc_id(pri,
03946 subcmd->u.cc_remote_user_free.cc_id);
03947 if (!monitor) {
03948 pri_cc_cancel(pri->pri, subcmd->u.cc_remote_user_free.cc_id);
03949 break;
03950 }
03951 ast_cc_monitor_callee_available(monitor->core_id,
03952 "%s callee has become available", sig_pri_cc_type_name);
03953 ao2_ref(monitor, -1);
03954 break;
03955 #endif
03956 #if defined(HAVE_PRI_CCSS)
03957 case PRI_SUBCMD_CC_B_FREE:
03958 monitor = sig_pri_find_cc_monitor_by_cc_id(pri,
03959 subcmd->u.cc_b_free.cc_id);
03960 if (!monitor) {
03961 pri_cc_cancel(pri->pri, subcmd->u.cc_b_free.cc_id);
03962 break;
03963 }
03964 ast_cc_monitor_party_b_free(monitor->core_id);
03965 ao2_ref(monitor, -1);
03966 break;
03967 #endif
03968 #if defined(HAVE_PRI_CCSS)
03969 case PRI_SUBCMD_CC_STATUS_REQ:
03970 monitor = sig_pri_find_cc_monitor_by_cc_id(pri,
03971 subcmd->u.cc_status_req.cc_id);
03972 if (!monitor) {
03973 pri_cc_cancel(pri->pri, subcmd->u.cc_status_req.cc_id);
03974 break;
03975 }
03976 ast_cc_monitor_status_request(monitor->core_id);
03977 ao2_ref(monitor, -1);
03978 break;
03979 #endif
03980 #if defined(HAVE_PRI_CCSS)
03981 case PRI_SUBCMD_CC_STATUS_REQ_RSP:
03982 agent = sig_pri_find_cc_agent_by_cc_id(pri, subcmd->u.cc_status_req_rsp.cc_id);
03983 if (!agent) {
03984 pri_cc_cancel(pri->pri, subcmd->u.cc_status_req_rsp.cc_id);
03985 break;
03986 }
03987 ast_cc_agent_status_response(agent->core_id,
03988 subcmd->u.cc_status_req_rsp.status ? AST_DEVICE_INUSE
03989 : AST_DEVICE_NOT_INUSE);
03990 ao2_ref(agent, -1);
03991 break;
03992 #endif
03993 #if defined(HAVE_PRI_CCSS)
03994 case PRI_SUBCMD_CC_STATUS:
03995 agent = sig_pri_find_cc_agent_by_cc_id(pri, subcmd->u.cc_status.cc_id);
03996 if (!agent) {
03997 pri_cc_cancel(pri->pri, subcmd->u.cc_status.cc_id);
03998 break;
03999 }
04000 if (subcmd->u.cc_status.status) {
04001 ast_cc_agent_caller_busy(agent->core_id, "%s agent caller is busy",
04002 sig_pri_cc_type_name);
04003 } else {
04004 ast_cc_agent_caller_available(agent->core_id,
04005 "%s agent caller is available", sig_pri_cc_type_name);
04006 }
04007 ao2_ref(agent, -1);
04008 break;
04009 #endif
04010 #if defined(HAVE_PRI_CCSS)
04011 case PRI_SUBCMD_CC_CANCEL:
04012 sig_pri_cc_link_canceled(pri, subcmd->u.cc_cancel.cc_id,
04013 subcmd->u.cc_cancel.is_agent);
04014 break;
04015 #endif
04016 #if defined(HAVE_PRI_CCSS)
04017 case PRI_SUBCMD_CC_STOP_ALERTING:
04018 monitor = sig_pri_find_cc_monitor_by_cc_id(pri,
04019 subcmd->u.cc_stop_alerting.cc_id);
04020 if (!monitor) {
04021 pri_cc_cancel(pri->pri, subcmd->u.cc_stop_alerting.cc_id);
04022 break;
04023 }
04024 ast_cc_monitor_stop_ringing(monitor->core_id);
04025 ao2_ref(monitor, -1);
04026 break;
04027 #endif
04028 #if defined(HAVE_PRI_AOC_EVENTS)
04029 case PRI_SUBCMD_AOC_E:
04030
04031 sig_pri_aoc_e_from_pri(&subcmd->u.aoc_e, NULL, 0);
04032 break;
04033 #endif
04034 default:
04035 ast_debug(2,
04036 "Unknown CIS subcommand(%d) in %s event on span %d.\n",
04037 subcmd->cmd, pri_event2str(event_id), pri->span);
04038 break;
04039 }
04040 }
04041 }
04042
04043 #if defined(HAVE_PRI_AOC_EVENTS)
04044
04045
04046
04047
04048
04049
04050
04051
04052
04053
04054
04055
04056
04057
04058
04059
04060
04061
04062
04063 static int detect_aoc_e_subcmd(const struct pri_subcommands *subcmds)
04064 {
04065 int i;
04066
04067 if (!subcmds) {
04068 return 0;
04069 }
04070 for (i = 0; i < subcmds->counter_subcmd; ++i) {
04071 const struct pri_subcommand *subcmd = &subcmds->subcmd[i];
04072 if (subcmd->cmd == PRI_SUBCMD_AOC_E) {
04073 return 1;
04074 }
04075 }
04076 return 0;
04077 }
04078 #endif
04079
04080
04081
04082
04083
04084
04085
04086
04087
04088
04089
04090
04091
04092
04093
04094
04095
04096
04097
04098
04099
04100 static void sig_pri_handle_subcmds(struct sig_pri_span *pri, int chanpos, int event_id,
04101 int channel, const struct pri_subcommands *subcmds, q931_call *call_rsp)
04102 {
04103 int index;
04104 struct ast_channel *owner;
04105 struct ast_party_redirecting ast_redirecting;
04106 #if defined(HAVE_PRI_TRANSFER)
04107 struct xfer_rsp_data xfer_rsp;
04108 #endif
04109
04110 if (!subcmds) {
04111 return;
04112 }
04113 for (index = 0; index < subcmds->counter_subcmd; ++index) {
04114 const struct pri_subcommand *subcmd = &subcmds->subcmd[index];
04115
04116 switch (subcmd->cmd) {
04117 case PRI_SUBCMD_CONNECTED_LINE:
04118 sig_pri_lock_owner(pri, chanpos);
04119 owner = pri->pvts[chanpos]->owner;
04120 if (owner) {
04121 struct ast_party_connected_line ast_connected;
04122 int caller_id_update;
04123
04124
04125 ast_party_connected_line_init(&ast_connected);
04126 sig_pri_party_id_convert(&ast_connected.id, &subcmd->u.connected_line.id,
04127 pri);
04128 ast_connected.id.tag = ast_strdup(pri->pvts[chanpos]->user_tag);
04129
04130 caller_id_update = 0;
04131 if (ast_connected.id.name.str) {
04132
04133 ast_copy_string(pri->pvts[chanpos]->cid_name,
04134 ast_connected.id.name.str, sizeof(pri->pvts[chanpos]->cid_name));
04135 caller_id_update = 1;
04136 }
04137 if (ast_connected.id.number.str) {
04138
04139 ast_copy_string(pri->pvts[chanpos]->cid_num,
04140 ast_connected.id.number.str, sizeof(pri->pvts[chanpos]->cid_num));
04141 pri->pvts[chanpos]->cid_ton = ast_connected.id.number.plan;
04142 caller_id_update = 1;
04143 }
04144 ast_connected.source = AST_CONNECTED_LINE_UPDATE_SOURCE_ANSWER;
04145
04146 pri->pvts[chanpos]->cid_subaddr[0] = '\0';
04147 #if defined(HAVE_PRI_SUBADDR)
04148 if (ast_connected.id.subaddress.valid) {
04149 ast_party_subaddress_set(&owner->caller.id.subaddress,
04150 &ast_connected.id.subaddress);
04151 if (ast_connected.id.subaddress.str) {
04152 ast_copy_string(pri->pvts[chanpos]->cid_subaddr,
04153 ast_connected.id.subaddress.str,
04154 sizeof(pri->pvts[chanpos]->cid_subaddr));
04155 }
04156 }
04157 #endif
04158 if (caller_id_update) {
04159 struct ast_party_caller ast_caller;
04160
04161 pri->pvts[chanpos]->callingpres =
04162 ast_party_id_presentation(&ast_connected.id);
04163 sig_pri_set_caller_id(pri->pvts[chanpos]);
04164
04165 ast_party_caller_set_init(&ast_caller, &owner->caller);
04166 ast_caller.id = ast_connected.id;
04167 ast_caller.ani = ast_connected.id;
04168 ast_channel_set_caller_event(owner, &ast_caller, NULL);
04169 }
04170
04171
04172 if (event_id != PRI_EVENT_RING) {
04173
04174 ast_channel_queue_connected_line_update(owner, &ast_connected, NULL);
04175 }
04176
04177 ast_party_connected_line_free(&ast_connected);
04178 ast_channel_unlock(owner);
04179 }
04180 break;
04181 case PRI_SUBCMD_REDIRECTING:
04182 sig_pri_lock_owner(pri, chanpos);
04183 owner = pri->pvts[chanpos]->owner;
04184 if (owner) {
04185 sig_pri_redirecting_convert(&ast_redirecting, &subcmd->u.redirecting,
04186 &owner->redirecting, pri);
04187 ast_redirecting.from.tag = ast_strdup(pri->pvts[chanpos]->user_tag);
04188 ast_redirecting.to.tag = ast_strdup(pri->pvts[chanpos]->user_tag);
04189
04190
04191
04192 ast_channel_set_redirecting(owner, &ast_redirecting, NULL);
04193 if (event_id != PRI_EVENT_RING) {
04194
04195 ast_channel_queue_redirecting_update(owner, &ast_redirecting, NULL);
04196 }
04197 ast_party_redirecting_free(&ast_redirecting);
04198
04199 ast_channel_unlock(owner);
04200 }
04201 break;
04202 #if defined(HAVE_PRI_CALL_REROUTING)
04203 case PRI_SUBCMD_REROUTING:
04204 sig_pri_lock_owner(pri, chanpos);
04205 owner = pri->pvts[chanpos]->owner;
04206 if (owner) {
04207 struct pri_party_redirecting pri_deflection;
04208
04209 if (!call_rsp) {
04210 ast_log(LOG_WARNING,
04211 "Span %d: %s tried CallRerouting/CallDeflection to '%s' without call!\n",
04212 pri->span, owner->name, subcmd->u.rerouting.deflection.to.number.str);
04213 ast_channel_unlock(owner);
04214 break;
04215 }
04216 if (ast_strlen_zero(subcmd->u.rerouting.deflection.to.number.str)) {
04217 ast_log(LOG_WARNING,
04218 "Span %d: %s tried CallRerouting/CallDeflection to empty number!\n",
04219 pri->span, owner->name);
04220 pri_rerouting_rsp(pri->pri, call_rsp, subcmd->u.rerouting.invoke_id,
04221 PRI_REROUTING_RSP_INVALID_NUMBER);
04222 ast_channel_unlock(owner);
04223 break;
04224 }
04225
04226 ast_verb(3, "Span %d: %s is CallRerouting/CallDeflection to '%s'.\n",
04227 pri->span, owner->name, subcmd->u.rerouting.deflection.to.number.str);
04228
04229
04230
04231
04232
04233
04234
04235 pri_rerouting_rsp(pri->pri, call_rsp, subcmd->u.rerouting.invoke_id,
04236 PRI_REROUTING_RSP_OK_CLEAR);
04237
04238 pri_deflection = subcmd->u.rerouting.deflection;
04239
04240
04241 switch (subcmd->u.rerouting.subscription_option) {
04242 case 0:
04243 case 1:
04244
04245 pri_deflection.to.number.presentation =
04246 PRI_PRES_RESTRICTED | PRI_PRES_USER_NUMBER_UNSCREENED;
04247 pri_deflection.to.number.plan =
04248 (PRI_TON_UNKNOWN << 4) | PRI_NPI_E163_E164;
04249 pri_deflection.to.number.str[0] = '\0';
04250 break;
04251 case 2:
04252 break;
04253 case 3:
04254 default:
04255 break;
04256 }
04257 sig_pri_redirecting_convert(&ast_redirecting, &pri_deflection,
04258 &owner->redirecting, pri);
04259 ast_redirecting.from.tag = ast_strdup(pri->pvts[chanpos]->user_tag);
04260 ast_redirecting.to.tag = ast_strdup(pri->pvts[chanpos]->user_tag);
04261 ast_channel_set_redirecting(owner, &ast_redirecting, NULL);
04262 ast_party_redirecting_free(&ast_redirecting);
04263
04264
04265 ast_string_field_set(owner, call_forward,
04266 subcmd->u.rerouting.deflection.to.number.str);
04267
04268
04269 ast_queue_frame(owner, &ast_null_frame);
04270
04271 ast_channel_unlock(owner);
04272 }
04273 break;
04274 #endif
04275 #if defined(HAVE_PRI_CCSS)
04276 case PRI_SUBCMD_CC_AVAILABLE:
04277 sig_pri_lock_owner(pri, chanpos);
04278 owner = pri->pvts[chanpos]->owner;
04279 if (owner) {
04280 enum ast_cc_service_type service;
04281
04282 switch (event_id) {
04283 case PRI_EVENT_RINGING:
04284 service = AST_CC_CCNR;
04285 break;
04286 case PRI_EVENT_HANGUP_REQ:
04287
04288 service = AST_CC_CCBS;
04289 break;
04290 default:
04291 service = AST_CC_NONE;
04292 break;
04293 }
04294 if (service == AST_CC_NONE
04295 || sig_pri_cc_available(pri, chanpos, subcmd->u.cc_available.cc_id,
04296 service)) {
04297 pri_cc_cancel(pri->pri, subcmd->u.cc_available.cc_id);
04298 }
04299 ast_channel_unlock(owner);
04300 } else {
04301
04302 pri_cc_cancel(pri->pri, subcmd->u.cc_available.cc_id);
04303 }
04304 break;
04305 #endif
04306 #if defined(HAVE_PRI_CCSS)
04307 case PRI_SUBCMD_CC_CALL:
04308 sig_pri_lock_owner(pri, chanpos);
04309 owner = pri->pvts[chanpos]->owner;
04310 if (owner) {
04311 struct ast_cc_agent *agent;
04312
04313 agent = sig_pri_find_cc_agent_by_cc_id(pri, subcmd->u.cc_call.cc_id);
04314 if (agent) {
04315 ast_setup_cc_recall_datastore(owner, agent->core_id);
04316 ast_cc_agent_set_interfaces_chanvar(owner);
04317 ast_cc_agent_recalling(agent->core_id,
04318 "%s caller is attempting recall", sig_pri_cc_type_name);
04319 ao2_ref(agent, -1);
04320 }
04321
04322 ast_channel_unlock(owner);
04323 }
04324 break;
04325 #endif
04326 #if defined(HAVE_PRI_CCSS)
04327 case PRI_SUBCMD_CC_CANCEL:
04328 sig_pri_cc_link_canceled(pri, subcmd->u.cc_cancel.cc_id,
04329 subcmd->u.cc_cancel.is_agent);
04330 break;
04331 #endif
04332 #if defined(HAVE_PRI_TRANSFER)
04333 case PRI_SUBCMD_TRANSFER_CALL:
04334 if (!call_rsp) {
04335
04336 ast_log(LOG_ERROR,
04337 "Call transfer subcommand without call to send response!\n");
04338 break;
04339 }
04340
04341 sig_pri_unlock_private(pri->pvts[chanpos]);
04342 xfer_rsp.pri = pri;
04343 xfer_rsp.call = call_rsp;
04344 xfer_rsp.invoke_id = subcmd->u.transfer.invoke_id;
04345 sig_pri_attempt_transfer(pri,
04346 subcmd->u.transfer.call_1, subcmd->u.transfer.is_call_1_held,
04347 subcmd->u.transfer.call_2, subcmd->u.transfer.is_call_2_held,
04348 sig_pri_transfer_rsp, &xfer_rsp);
04349 sig_pri_lock_private(pri->pvts[chanpos]);
04350 break;
04351 #endif
04352 #if defined(HAVE_PRI_AOC_EVENTS)
04353 case PRI_SUBCMD_AOC_S:
04354 sig_pri_lock_owner(pri, chanpos);
04355 owner = pri->pvts[chanpos]->owner;
04356 if (owner) {
04357 sig_pri_aoc_s_from_pri(&subcmd->u.aoc_s, owner,
04358 (pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_S));
04359 ast_channel_unlock(owner);
04360 }
04361 break;
04362 #endif
04363 #if defined(HAVE_PRI_AOC_EVENTS)
04364 case PRI_SUBCMD_AOC_D:
04365 sig_pri_lock_owner(pri, chanpos);
04366 owner = pri->pvts[chanpos]->owner;
04367 if (owner) {
04368
04369 sig_pri_aoc_d_from_pri(&subcmd->u.aoc_d, owner,
04370 (pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_D));
04371 ast_channel_unlock(owner);
04372 }
04373 break;
04374 #endif
04375 #if defined(HAVE_PRI_AOC_EVENTS)
04376 case PRI_SUBCMD_AOC_E:
04377 sig_pri_lock_owner(pri, chanpos);
04378 owner = pri->pvts[chanpos]->owner;
04379
04380 sig_pri_aoc_e_from_pri(&subcmd->u.aoc_e, owner,
04381 (pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_E));
04382 if (owner) {
04383 ast_channel_unlock(owner);
04384 }
04385 break;
04386 #endif
04387 #if defined(HAVE_PRI_AOC_EVENTS)
04388 case PRI_SUBCMD_AOC_CHARGING_REQ:
04389 sig_pri_lock_owner(pri, chanpos);
04390 owner = pri->pvts[chanpos]->owner;
04391 if (owner) {
04392 sig_pri_aoc_request_from_pri(&subcmd->u.aoc_request, pri->pvts[chanpos],
04393 call_rsp);
04394 ast_channel_unlock(owner);
04395 }
04396 break;
04397 #endif
04398 #if defined(HAVE_PRI_AOC_EVENTS)
04399 case PRI_SUBCMD_AOC_CHARGING_REQ_RSP:
04400
04401
04402
04403
04404
04405 if (subcmd->u.aoc_request_response.valid_aoc_s) {
04406 sig_pri_lock_owner(pri, chanpos);
04407 owner = pri->pvts[chanpos]->owner;
04408 if (owner) {
04409 sig_pri_aoc_s_from_pri(&subcmd->u.aoc_request_response.aoc_s, owner,
04410 (pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_S));
04411 ast_channel_unlock(owner);
04412 }
04413 }
04414 break;
04415 #endif
04416 #if defined(HAVE_PRI_MCID)
04417 case PRI_SUBCMD_MCID_REQ:
04418 sig_pri_lock_owner(pri, chanpos);
04419 owner = pri->pvts[chanpos]->owner;
04420 sig_pri_mcid_event(pri, &subcmd->u.mcid_req, owner);
04421 if (owner) {
04422 ast_channel_unlock(owner);
04423 }
04424 break;
04425 #endif
04426 #if defined(HAVE_PRI_MCID)
04427 case PRI_SUBCMD_MCID_RSP:
04428
04429 break;
04430 #endif
04431 default:
04432 ast_debug(2,
04433 "Unknown call subcommand(%d) in %s event on channel %d/%d on span %d.\n",
04434 subcmd->cmd, pri_event2str(event_id), PRI_SPAN(channel),
04435 PRI_CHANNEL(channel), pri->span);
04436 break;
04437 }
04438 }
04439 }
04440
04441 #if defined(HAVE_PRI_CALL_HOLD)
04442
04443
04444
04445
04446
04447
04448
04449
04450
04451
04452
04453
04454
04455 static int sig_pri_handle_hold(struct sig_pri_span *pri, pri_event *ev)
04456 {
04457 int retval;
04458 int chanpos_old;
04459 int chanpos_new;
04460 struct ast_channel *owner;
04461
04462 chanpos_old = pri_find_principle_by_call(pri, ev->hold.call);
04463 if (chanpos_old < 0) {
04464 ast_log(LOG_WARNING, "Span %d: Received HOLD for unknown call.\n", pri->span);
04465 return -1;
04466 }
04467 if (pri->pvts[chanpos_old]->no_b_channel) {
04468
04469 return -1;
04470 }
04471
04472 chanpos_new = -1;
04473
04474 sig_pri_lock_private(pri->pvts[chanpos_old]);
04475 sig_pri_lock_owner(pri, chanpos_old);
04476 owner = pri->pvts[chanpos_old]->owner;
04477 if (!owner) {
04478 goto done_with_private;
04479 }
04480 if (pri->pvts[chanpos_old]->call_level != SIG_PRI_CALL_LEVEL_CONNECT) {
04481
04482
04483
04484
04485 goto done_with_owner;
04486 }
04487 chanpos_new = pri_find_empty_nobch(pri);
04488 if (chanpos_new < 0) {
04489
04490 goto done_with_owner;
04491 }
04492 sig_pri_handle_subcmds(pri, chanpos_old, ev->e, ev->hold.channel, ev->hold.subcmds,
04493 ev->hold.call);
04494 chanpos_new = pri_fixup_principle(pri, chanpos_new, ev->hold.call);
04495 if (chanpos_new < 0) {
04496
04497 } else {
04498 struct ast_frame f = { AST_FRAME_CONTROL, };
04499
04500
04501
04502
04503
04504 f.subclass.integer = AST_CONTROL_HOLD;
04505 ast_queue_frame(owner, &f);
04506 }
04507
04508 done_with_owner:;
04509 ast_channel_unlock(owner);
04510 done_with_private:;
04511 sig_pri_unlock_private(pri->pvts[chanpos_old]);
04512
04513 if (chanpos_new < 0) {
04514 retval = -1;
04515 } else {
04516 sig_pri_span_devstate_changed(pri);
04517 retval = 0;
04518 }
04519
04520 return retval;
04521 }
04522 #endif
04523
04524 #if defined(HAVE_PRI_CALL_HOLD)
04525
04526
04527
04528
04529
04530
04531
04532
04533
04534
04535
04536
04537 static void sig_pri_handle_retrieve(struct sig_pri_span *pri, pri_event *ev)
04538 {
04539 int chanpos;
04540
04541 if (!(ev->retrieve.channel & PRI_HELD_CALL)) {
04542
04543 pri_retrieve_rej(pri->pri, ev->retrieve.call,
04544 PRI_CAUSE_RESOURCE_UNAVAIL_UNSPECIFIED);
04545 return;
04546 }
04547 if (pri_find_principle_by_call(pri, ev->retrieve.call) < 0) {
04548 ast_log(LOG_WARNING, "Span %d: Received RETRIEVE for unknown call.\n", pri->span);
04549 pri_retrieve_rej(pri->pri, ev->retrieve.call,
04550 PRI_CAUSE_RESOURCE_UNAVAIL_UNSPECIFIED);
04551 return;
04552 }
04553 if (PRI_CHANNEL(ev->retrieve.channel) == 0xFF) {
04554 chanpos = pri_find_empty_chan(pri, 1);
04555 } else {
04556 chanpos = pri_find_principle(pri,
04557 ev->retrieve.channel & ~PRI_HELD_CALL, ev->retrieve.call);
04558 if (ev->retrieve.flexible
04559 && (chanpos < 0 || !sig_pri_is_chan_available(pri->pvts[chanpos]))) {
04560
04561
04562
04563
04564 chanpos = pri_find_empty_chan(pri, 1);
04565 }
04566 }
04567 if (chanpos < 0) {
04568 pri_retrieve_rej(pri->pri, ev->retrieve.call,
04569 ev->retrieve.flexible ? PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION
04570 : PRI_CAUSE_REQUESTED_CHAN_UNAVAIL);
04571 return;
04572 }
04573 chanpos = pri_fixup_principle(pri, chanpos, ev->retrieve.call);
04574 if (chanpos < 0) {
04575
04576 pri_retrieve_rej(pri->pri, ev->retrieve.call,
04577 PRI_CAUSE_REQUESTED_CHAN_UNAVAIL);
04578 return;
04579 }
04580 sig_pri_lock_private(pri->pvts[chanpos]);
04581 sig_pri_handle_subcmds(pri, chanpos, ev->e, ev->retrieve.channel,
04582 ev->retrieve.subcmds, ev->retrieve.call);
04583 pri_queue_control(pri, chanpos, AST_CONTROL_UNHOLD);
04584 sig_pri_unlock_private(pri->pvts[chanpos]);
04585 pri_retrieve_ack(pri->pri, ev->retrieve.call,
04586 PVT_TO_CHANNEL(pri->pvts[chanpos]));
04587 sig_pri_span_devstate_changed(pri);
04588 }
04589 #endif
04590
04591 static void *pri_dchannel(void *vpri)
04592 {
04593 struct sig_pri_span *pri = vpri;
04594 pri_event *e;
04595 struct pollfd fds[SIG_PRI_NUM_DCHANS];
04596 int res;
04597 int chanpos = 0;
04598 int x;
04599 int law;
04600 struct ast_channel *c;
04601 struct timeval tv, lowest, *next;
04602 int doidling=0;
04603 char *cc;
04604 time_t t;
04605 int i, which=-1;
04606 int numdchans;
04607 pthread_t threadid;
04608 char ani2str[6];
04609 char plancallingnum[AST_MAX_EXTENSION];
04610 char plancallingani[AST_MAX_EXTENSION];
04611 char calledtonstr[10];
04612 struct timeval lastidle = { 0, 0 };
04613 pthread_t p;
04614 struct ast_channel *idle;
04615 char idlen[80];
04616 int nextidle = -1;
04617 int haveidles;
04618 int activeidles;
04619 unsigned int len;
04620
04621 gettimeofday(&lastidle, NULL);
04622 pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, NULL);
04623
04624 if (!ast_strlen_zero(pri->idledial) && !ast_strlen_zero(pri->idleext)) {
04625
04626 cc = strchr(pri->idleext, '@');
04627 if (cc) {
04628 *cc = '\0';
04629 cc++;
04630 ast_copy_string(pri->idlecontext, cc, sizeof(pri->idlecontext));
04631 #if 0
04632
04633 if (!ast_exists_extension(NULL, pri->idlecontext, pri->idleext, 1, NULL))
04634 ast_log(LOG_WARNING, "Extension '%s @ %s' does not exist\n", pri->idleext, pri->idlecontext);
04635 else
04636 #endif
04637 doidling = 1;
04638 } else
04639 ast_log(LOG_WARNING, "Idle dial string '%s' lacks '@context'\n", pri->idleext);
04640 }
04641 for (;;) {
04642 for (i = 0; i < SIG_PRI_NUM_DCHANS; i++) {
04643 if (!pri->dchans[i])
04644 break;
04645 fds[i].fd = pri->fds[i];
04646 fds[i].events = POLLIN | POLLPRI;
04647 fds[i].revents = 0;
04648 }
04649 numdchans = i;
04650 time(&t);
04651 ast_mutex_lock(&pri->lock);
04652 if (pri->switchtype != PRI_SWITCH_GR303_TMC && (pri->sig != SIG_BRI_PTMP) && (pri->resetinterval > 0)) {
04653 if (pri->resetting && pri_is_up(pri)) {
04654 if (pri->resetpos < 0) {
04655 pri_check_restart(pri);
04656 if (pri->resetting) {
04657 sig_pri_span_devstate_changed(pri);
04658 }
04659 }
04660 } else {
04661 if (!pri->resetting && (t - pri->lastreset) >= pri->resetinterval) {
04662 pri->resetting = 1;
04663 pri->resetpos = -1;
04664 }
04665 }
04666 }
04667
04668 if (doidling && pri_is_up(pri)) {
04669 nextidle = -1;
04670 haveidles = 0;
04671 activeidles = 0;
04672 for (x = pri->numchans; x >= 0; x--) {
04673 if (pri->pvts[x] && !pri->pvts[x]->no_b_channel) {
04674 if (sig_pri_is_chan_available(pri->pvts[x])) {
04675 if (haveidles < pri->minunused) {
04676 haveidles++;
04677 } else {
04678 nextidle = x;
04679 break;
04680 }
04681 } else if (pri->pvts[x]->owner && pri->pvts[x]->isidlecall) {
04682 activeidles++;
04683 }
04684 }
04685 }
04686 if (nextidle > -1) {
04687 if (ast_tvdiff_ms(ast_tvnow(), lastidle) > 1000) {
04688
04689 snprintf(idlen, sizeof(idlen), "%d/%s", pri->pvts[nextidle]->channel, pri->idledial);
04690 pri->pvts[nextidle]->allocated = 1;
04691
04692
04693
04694
04695 ast_mutex_unlock(&pri->lock);
04696
04697
04698
04699
04700
04701 sig_pri_lock_private(pri->pvts[nextidle]);
04702 sig_pri_unlock_private(pri->pvts[nextidle]);
04703 idle = sig_pri_request(pri->pvts[nextidle], AST_FORMAT_ULAW, NULL, 0);
04704 ast_mutex_lock(&pri->lock);
04705 if (idle) {
04706 pri->pvts[nextidle]->isidlecall = 1;
04707 if (ast_pthread_create_background(&p, NULL, do_idle_thread, pri->pvts[nextidle])) {
04708 ast_log(LOG_WARNING, "Unable to start new thread for idle channel '%s'\n", idle->name);
04709 ast_mutex_unlock(&pri->lock);
04710 ast_hangup(idle);
04711 ast_mutex_lock(&pri->lock);
04712 }
04713 } else {
04714 pri->pvts[nextidle]->allocated = 0;
04715 ast_log(LOG_WARNING, "Unable to request channel 'DAHDI/%s' for idle call\n", idlen);
04716 }
04717 gettimeofday(&lastidle, NULL);
04718 }
04719 } else if ((haveidles < pri->minunused) &&
04720 (activeidles > pri->minidle)) {
04721
04722
04723 for (x = pri->numchans; x >= 0; x--) {
04724
04725 if (pri->pvts[x] && pri->pvts[x]->owner && pri->pvts[x]->isidlecall) {
04726 pri->pvts[x]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
04727 haveidles++;
04728
04729
04730 if ((haveidles >= pri->minunused) ||
04731 (activeidles <= pri->minidle))
04732 break;
04733 }
04734 }
04735 }
04736 }
04737
04738 if (doidling || pri->resetting) {
04739
04740
04741
04742
04743 lowest = ast_tv(1, 0);
04744 } else {
04745
04746 lowest = ast_tv(60, 0);
04747 }
04748 for (i = 0; i < SIG_PRI_NUM_DCHANS; i++) {
04749 if (!pri->dchans[i]) {
04750
04751 break;
04752 }
04753 next = pri_schedule_next(pri->dchans[i]);
04754 if (next) {
04755
04756 tv = ast_tvsub(*next, ast_tvnow());
04757 if (tv.tv_sec < 0) {
04758
04759
04760
04761
04762 lowest = ast_tv(0, 0);
04763 break;
04764 }
04765 if (ast_tvcmp(tv, lowest) < 0) {
04766 lowest = tv;
04767 }
04768 }
04769 }
04770 ast_mutex_unlock(&pri->lock);
04771
04772 pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, NULL);
04773 pthread_testcancel();
04774 e = NULL;
04775 res = poll(fds, numdchans, lowest.tv_sec * 1000 + lowest.tv_usec / 1000);
04776 pthread_testcancel();
04777 pthread_setcancelstate(PTHREAD_CANCEL_DISABLE, NULL);
04778
04779 ast_mutex_lock(&pri->lock);
04780 if (!res) {
04781 for (which = 0; which < SIG_PRI_NUM_DCHANS; which++) {
04782 if (!pri->dchans[which])
04783 break;
04784
04785 e = pri_schedule_run(pri->dchans[which]);
04786 if (e)
04787 break;
04788 }
04789 } else if (res > -1) {
04790 for (which = 0; which < SIG_PRI_NUM_DCHANS; which++) {
04791 if (!pri->dchans[which])
04792 break;
04793 if (fds[which].revents & POLLPRI) {
04794 sig_pri_handle_dchan_exception(pri, which);
04795 } else if (fds[which].revents & POLLIN) {
04796 e = pri_check_event(pri->dchans[which]);
04797 }
04798 if (e)
04799 break;
04800 }
04801 } else if (errno != EINTR)
04802 ast_log(LOG_WARNING, "pri_event returned error %d (%s)\n", errno, strerror(errno));
04803
04804 if (e) {
04805 if (pri->debug) {
04806 ast_verbose("Span %d: Processing event %s\n",
04807 pri->span, pri_event2str(e->e));
04808 }
04809
04810 if (e->e != PRI_EVENT_DCHAN_DOWN) {
04811 if (!(pri->dchanavail[which] & DCHAN_UP)) {
04812 ast_verb(2, "%s D-Channel on span %d up\n", pri_order(which), pri->span);
04813 }
04814 pri->dchanavail[which] |= DCHAN_UP;
04815 } else {
04816 if (pri->dchanavail[which] & DCHAN_UP) {
04817 ast_verb(2, "%s D-Channel on span %d down\n", pri_order(which), pri->span);
04818 }
04819 pri->dchanavail[which] &= ~DCHAN_UP;
04820 }
04821
04822 if ((e->e != PRI_EVENT_DCHAN_UP) && (e->e != PRI_EVENT_DCHAN_DOWN) && (pri->pri != pri->dchans[which]))
04823
04824 pri->pri = pri->dchans[which];
04825
04826 switch (e->e) {
04827 case PRI_EVENT_DCHAN_UP:
04828 pri->no_d_channels = 0;
04829 if (!pri->pri) {
04830 pri_find_dchan(pri);
04831 }
04832
04833
04834 time(&pri->lastreset);
04835
04836
04837 if (pri->resetinterval > -1) {
04838 pri->lastreset -= pri->resetinterval;
04839 pri->lastreset += 5;
04840 }
04841
04842 pri->resetting = 0;
04843 for (i = 0; i < pri->numchans; i++) {
04844 if (pri->pvts[i]) {
04845 sig_pri_set_alarm(pri->pvts[i], 0);
04846 }
04847 }
04848 sig_pri_span_devstate_changed(pri);
04849 break;
04850 case PRI_EVENT_DCHAN_DOWN:
04851 pri_find_dchan(pri);
04852 if (!pri_is_up(pri)) {
04853 if (pri->sig == SIG_BRI_PTMP) {
04854
04855
04856
04857
04858 break;
04859 }
04860
04861 pri->resetting = 0;
04862 for (i = 0; i < pri->numchans; i++) {
04863 struct sig_pri_chan *p = pri->pvts[i];
04864
04865 if (p) {
04866 if (pri_get_timer(p->pri->pri, PRI_TIMER_T309) < 0) {
04867
04868 if (p->call) {
04869 pri_destroycall(p->pri->pri, p->call);
04870 p->call = NULL;
04871 }
04872 if (p->owner)
04873 p->owner->_softhangup |= AST_SOFTHANGUP_DEV;
04874 }
04875 sig_pri_set_alarm(p, 1);
04876 }
04877 }
04878 sig_pri_span_devstate_changed(pri);
04879 }
04880 break;
04881 case PRI_EVENT_RESTART:
04882 if (e->restart.channel > -1 && PRI_CHANNEL(e->restart.channel) != 0xFF) {
04883 chanpos = pri_find_principle(pri, e->restart.channel, NULL);
04884 if (chanpos < 0)
04885 ast_log(LOG_WARNING,
04886 "Span %d: Restart requested on odd/unavailable channel number %d/%d\n",
04887 pri->span, PRI_SPAN(e->restart.channel),
04888 PRI_CHANNEL(e->restart.channel));
04889 else {
04890 int skipit = 0;
04891 #if defined(HAVE_PRI_SERVICE_MESSAGES)
04892 unsigned why;
04893
04894 why = pri->pvts[chanpos]->service_status;
04895 if (why) {
04896 ast_log(LOG_NOTICE,
04897 "Span %d: Channel %d/%d out-of-service (reason: %s), ignoring RESTART\n",
04898 pri->span, PRI_SPAN(e->restart.channel),
04899 PRI_CHANNEL(e->restart.channel),
04900 (why & SRVST_FAREND) ? (why & SRVST_NEAREND) ? "both ends" : "far end" : "near end");
04901 skipit = 1;
04902 }
04903 #endif
04904 sig_pri_lock_private(pri->pvts[chanpos]);
04905 if (!skipit) {
04906 ast_verb(3, "Span %d: Channel %d/%d restarted\n", pri->span,
04907 PRI_SPAN(e->restart.channel),
04908 PRI_CHANNEL(e->restart.channel));
04909 if (pri->pvts[chanpos]->call) {
04910 pri_destroycall(pri->pri, pri->pvts[chanpos]->call);
04911 pri->pvts[chanpos]->call = NULL;
04912 }
04913 }
04914
04915 if (pri->pvts[chanpos]->owner)
04916 pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
04917 sig_pri_unlock_private(pri->pvts[chanpos]);
04918 }
04919 } else {
04920 ast_verb(3, "Restart requested on entire span %d\n", pri->span);
04921 for (x = 0; x < pri->numchans; x++)
04922 if (pri->pvts[x]) {
04923 sig_pri_lock_private(pri->pvts[x]);
04924 if (pri->pvts[x]->call) {
04925 pri_destroycall(pri->pri, pri->pvts[x]->call);
04926 pri->pvts[x]->call = NULL;
04927 }
04928 if (pri->pvts[x]->owner)
04929 pri->pvts[x]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
04930 sig_pri_unlock_private(pri->pvts[x]);
04931 }
04932 }
04933 sig_pri_span_devstate_changed(pri);
04934 break;
04935 case PRI_EVENT_KEYPAD_DIGIT:
04936 if (sig_pri_is_cis_call(e->digit.channel)) {
04937 sig_pri_handle_cis_subcmds(pri, e->e, e->digit.subcmds,
04938 e->digit.call);
04939 break;
04940 }
04941 chanpos = pri_find_principle_by_call(pri, e->digit.call);
04942 if (chanpos < 0) {
04943 ast_log(LOG_WARNING,
04944 "Span %d: Received keypad digits for unknown call.\n", pri->span);
04945 break;
04946 }
04947 sig_pri_lock_private(pri->pvts[chanpos]);
04948 sig_pri_handle_subcmds(pri, chanpos, e->e, e->digit.channel,
04949 e->digit.subcmds, e->digit.call);
04950
04951 if ((pri->overlapdial & DAHDI_OVERLAPDIAL_INCOMING)
04952 && pri->pvts[chanpos]->owner) {
04953
04954 int digitlen = strlen(e->digit.digits);
04955 int i;
04956
04957 for (i = 0; i < digitlen; i++) {
04958 struct ast_frame f = { AST_FRAME_DTMF, .subclass.integer = e->digit.digits[i], };
04959
04960 pri_queue_frame(pri, chanpos, &f);
04961 }
04962 }
04963 sig_pri_unlock_private(pri->pvts[chanpos]);
04964 break;
04965
04966 case PRI_EVENT_INFO_RECEIVED:
04967 if (sig_pri_is_cis_call(e->ring.channel)) {
04968 sig_pri_handle_cis_subcmds(pri, e->e, e->ring.subcmds,
04969 e->ring.call);
04970 break;
04971 }
04972 chanpos = pri_find_principle_by_call(pri, e->ring.call);
04973 if (chanpos < 0) {
04974 ast_log(LOG_WARNING,
04975 "Span %d: Received INFORMATION for unknown call.\n", pri->span);
04976 break;
04977 }
04978 sig_pri_lock_private(pri->pvts[chanpos]);
04979 sig_pri_handle_subcmds(pri, chanpos, e->e, e->ring.channel,
04980 e->ring.subcmds, e->ring.call);
04981
04982 if ((pri->overlapdial & DAHDI_OVERLAPDIAL_INCOMING)
04983 && pri->pvts[chanpos]->owner) {
04984
04985 int digitlen = strlen(e->ring.callednum);
04986 int i;
04987
04988 for (i = 0; i < digitlen; i++) {
04989 struct ast_frame f = { AST_FRAME_DTMF, .subclass.integer = e->ring.callednum[i], };
04990
04991 pri_queue_frame(pri, chanpos, &f);
04992 }
04993 }
04994 sig_pri_unlock_private(pri->pvts[chanpos]);
04995 break;
04996 #if defined(HAVE_PRI_SERVICE_MESSAGES)
04997 case PRI_EVENT_SERVICE:
04998 chanpos = pri_find_principle(pri, e->service.channel, NULL);
04999 if (chanpos < 0) {
05000 ast_log(LOG_WARNING, "Received service change status %d on unconfigured channel %d/%d span %d\n",
05001 e->service_ack.changestatus, PRI_SPAN(e->service_ack.channel), PRI_CHANNEL(e->service_ack.channel), pri->span);
05002 } else {
05003 char db_chan_name[20];
05004 char db_answer[5];
05005 int ch;
05006 unsigned *why;
05007
05008 ch = pri->pvts[chanpos]->channel;
05009 snprintf(db_chan_name, sizeof(db_chan_name), "%s/%d:%d", dahdi_db, pri->span, ch);
05010 why = &pri->pvts[chanpos]->service_status;
05011 switch (e->service.changestatus) {
05012 case 0:
05013
05014 ast_db_del(db_chan_name, SRVST_DBKEY);
05015 *why &= ~SRVST_FAREND;
05016 if (*why) {
05017 snprintf(db_answer, sizeof(db_answer), "%s:%u",
05018 SRVST_TYPE_OOS, *why);
05019 ast_db_put(db_chan_name, SRVST_DBKEY, db_answer);
05020 } else {
05021 sig_pri_span_devstate_changed(pri);
05022 }
05023 break;
05024 case 2:
05025
05026 ast_db_del(db_chan_name, SRVST_DBKEY);
05027 *why |= SRVST_FAREND;
05028 snprintf(db_answer, sizeof(db_answer), "%s:%u", SRVST_TYPE_OOS,
05029 *why);
05030 ast_db_put(db_chan_name, SRVST_DBKEY, db_answer);
05031 sig_pri_span_devstate_changed(pri);
05032 break;
05033 default:
05034 ast_log(LOG_ERROR, "Huh? changestatus is: %d\n", e->service.changestatus);
05035 break;
05036 }
05037 ast_log(LOG_NOTICE, "Channel %d/%d span %d (logical: %d) received a change of service message, status '%d'\n",
05038 PRI_SPAN(e->service.channel), PRI_CHANNEL(e->service.channel), pri->span, ch, e->service.changestatus);
05039 }
05040 break;
05041 case PRI_EVENT_SERVICE_ACK:
05042 chanpos = pri_find_principle(pri, e->service_ack.channel, NULL);
05043 if (chanpos < 0) {
05044 ast_log(LOG_WARNING, "Received service acknowledge change status '%d' on unconfigured channel %d/%d span %d\n",
05045 e->service_ack.changestatus, PRI_SPAN(e->service_ack.channel), PRI_CHANNEL(e->service_ack.channel), pri->span);
05046 } else {
05047 ast_debug(2, "Channel %d/%d span %d received a change os service acknowledgement message, status '%d'\n",
05048 PRI_SPAN(e->service_ack.channel), PRI_CHANNEL(e->service_ack.channel), pri->span, e->service_ack.changestatus);
05049 }
05050 break;
05051 #endif
05052 case PRI_EVENT_RING:
05053 if (!ast_strlen_zero(pri->msn_list)
05054 && !sig_pri_msn_match(pri->msn_list, e->ring.callednum)) {
05055
05056 ast_verb(3,
05057 "Ignoring call to '%s' on span %d. Its not in the MSN list: %s\n",
05058 e->ring.callednum, pri->span, pri->msn_list);
05059 pri_destroycall(pri->pri, e->ring.call);
05060 break;
05061 }
05062 if (sig_pri_is_cis_call(e->ring.channel)) {
05063 sig_pri_handle_cis_subcmds(pri, e->e, e->ring.subcmds,
05064 e->ring.call);
05065 break;
05066 }
05067 chanpos = pri_find_principle_by_call(pri, e->ring.call);
05068 if (-1 < chanpos) {
05069
05070 ast_log(LOG_WARNING,
05071 "Span %d: Got SETUP with duplicate call ptr (%p). Dropping call.\n",
05072 pri->span, e->ring.call);
05073 pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_NORMAL_TEMPORARY_FAILURE);
05074 break;
05075 }
05076 if (e->ring.channel == -1 || PRI_CHANNEL(e->ring.channel) == 0xFF) {
05077
05078 chanpos = pri_find_empty_chan(pri, 1);
05079 } else if (PRI_CHANNEL(e->ring.channel) == 0x00) {
05080
05081 #if defined(HAVE_PRI_CALL_WAITING)
05082 if (!pri->allow_call_waiting_calls)
05083 #endif
05084 {
05085
05086 pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION);
05087 break;
05088 }
05089 #if defined(HAVE_PRI_CALL_WAITING)
05090 chanpos = pri_find_empty_nobch(pri);
05091 if (chanpos < 0) {
05092
05093 pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION);
05094 break;
05095 }
05096
05097 sig_pri_init_config(pri->pvts[chanpos], pri);
05098 #endif
05099 } else {
05100
05101 chanpos = pri_find_principle(pri, e->ring.channel, e->ring.call);
05102 if (chanpos < 0) {
05103 ast_log(LOG_WARNING,
05104 "Span %d: SETUP on unconfigured channel %d/%d\n",
05105 pri->span, PRI_SPAN(e->ring.channel),
05106 PRI_CHANNEL(e->ring.channel));
05107 } else {
05108 switch (pri->pvts[chanpos]->resetting) {
05109 case SIG_PRI_RESET_IDLE:
05110 break;
05111 case SIG_PRI_RESET_ACTIVE:
05112
05113
05114
05115
05116 pri->pvts[chanpos]->resetting = SIG_PRI_RESET_NO_ACK;
05117 break;
05118 case SIG_PRI_RESET_NO_ACK:
05119
05120 ast_debug(1,
05121 "Span %d: Second SETUP while waiting for RESTART ACKNOWLEDGE on channel %d/%d\n",
05122 pri->span, PRI_SPAN(e->ring.channel),
05123 PRI_CHANNEL(e->ring.channel));
05124
05125
05126 pri->pvts[chanpos]->resetting = SIG_PRI_RESET_IDLE;
05127 if (pri->resetting) {
05128
05129 pri_check_restart(pri);
05130 }
05131 break;
05132 }
05133 if (!sig_pri_is_chan_available(pri->pvts[chanpos])) {
05134
05135 ast_debug(1,
05136 "Span %d: SETUP requested unavailable channel %d/%d. Attempting to renegotiate.\n",
05137 pri->span, PRI_SPAN(e->ring.channel),
05138 PRI_CHANNEL(e->ring.channel));
05139 chanpos = -1;
05140 }
05141 }
05142 #if defined(ALWAYS_PICK_CHANNEL)
05143 if (e->ring.flexible) {
05144 chanpos = -1;
05145 }
05146 #endif
05147 if (chanpos < 0 && e->ring.flexible) {
05148
05149 chanpos = pri_find_empty_chan(pri, 1);
05150 }
05151 }
05152 if (chanpos < 0) {
05153 if (e->ring.flexible) {
05154 pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION);
05155 } else {
05156 pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_REQUESTED_CHAN_UNAVAIL);
05157 }
05158 break;
05159 }
05160
05161 sig_pri_lock_private(pri->pvts[chanpos]);
05162
05163
05164 pri->pvts[chanpos]->call = e->ring.call;
05165
05166
05167 apply_plan_to_existing_number(plancallingnum, sizeof(plancallingnum), pri,
05168 e->ring.redirectingnum, e->ring.callingplanrdnis);
05169 sig_pri_set_rdnis(pri->pvts[chanpos], plancallingnum);
05170
05171
05172 apply_plan_to_existing_number(plancallingnum, sizeof(plancallingnum), pri,
05173 e->ring.callingnum, e->ring.callingplan);
05174 pri->pvts[chanpos]->cid_ani2 = 0;
05175 if (pri->pvts[chanpos]->use_callerid) {
05176 ast_shrink_phone_number(plancallingnum);
05177 ast_copy_string(pri->pvts[chanpos]->cid_num, plancallingnum, sizeof(pri->pvts[chanpos]->cid_num));
05178 #ifdef PRI_ANI
05179 apply_plan_to_existing_number(plancallingani, sizeof(plancallingani),
05180 pri, e->ring.callingani, e->ring.callingplanani);
05181 ast_shrink_phone_number(plancallingani);
05182 ast_copy_string(pri->pvts[chanpos]->cid_ani, plancallingani,
05183 sizeof(pri->pvts[chanpos]->cid_ani));
05184 #endif
05185 pri->pvts[chanpos]->cid_subaddr[0] = '\0';
05186 #if defined(HAVE_PRI_SUBADDR)
05187 if (e->ring.calling.subaddress.valid) {
05188 struct ast_party_subaddress calling_subaddress;
05189
05190 ast_party_subaddress_init(&calling_subaddress);
05191 sig_pri_set_subaddress(&calling_subaddress,
05192 &e->ring.calling.subaddress);
05193 if (calling_subaddress.str) {
05194 ast_copy_string(pri->pvts[chanpos]->cid_subaddr,
05195 calling_subaddress.str,
05196 sizeof(pri->pvts[chanpos]->cid_subaddr));
05197 }
05198 ast_party_subaddress_free(&calling_subaddress);
05199 }
05200 #endif
05201 ast_copy_string(pri->pvts[chanpos]->cid_name, e->ring.callingname, sizeof(pri->pvts[chanpos]->cid_name));
05202 pri->pvts[chanpos]->cid_ton = e->ring.callingplan;
05203 pri->pvts[chanpos]->callingpres = e->ring.callingpres;
05204 if (e->ring.ani2 >= 0) {
05205 pri->pvts[chanpos]->cid_ani2 = e->ring.ani2;
05206 }
05207 } else {
05208 pri->pvts[chanpos]->cid_num[0] = '\0';
05209 pri->pvts[chanpos]->cid_subaddr[0] = '\0';
05210 pri->pvts[chanpos]->cid_ani[0] = '\0';
05211 pri->pvts[chanpos]->cid_name[0] = '\0';
05212 pri->pvts[chanpos]->cid_ton = 0;
05213 pri->pvts[chanpos]->callingpres = 0;
05214 }
05215
05216
05217 if (pri->append_msn_to_user_tag) {
05218 snprintf(pri->pvts[chanpos]->user_tag,
05219 sizeof(pri->pvts[chanpos]->user_tag), "%s_%s",
05220 pri->initial_user_tag,
05221 pri->nodetype == PRI_NETWORK
05222 ? plancallingnum : e->ring.callednum);
05223 } else {
05224 ast_copy_string(pri->pvts[chanpos]->user_tag,
05225 pri->initial_user_tag, sizeof(pri->pvts[chanpos]->user_tag));
05226 }
05227
05228 sig_pri_set_caller_id(pri->pvts[chanpos]);
05229
05230
05231 sig_pri_set_dnid(pri->pvts[chanpos], e->ring.callednum);
05232
05233
05234 if (pri->pvts[chanpos]->immediate) {
05235 ast_verb(3, "Going to extension s|1 because of immediate=yes\n");
05236 pri->pvts[chanpos]->exten[0] = 's';
05237 pri->pvts[chanpos]->exten[1] = '\0';
05238 }
05239
05240 else if (!ast_strlen_zero(e->ring.callednum)) {
05241 ast_copy_string(pri->pvts[chanpos]->exten, e->ring.callednum, sizeof(pri->pvts[chanpos]->exten));
05242 } else if (pri->overlapdial)
05243 pri->pvts[chanpos]->exten[0] = '\0';
05244 else {
05245
05246 pri->pvts[chanpos]->exten[0] = 's';
05247 pri->pvts[chanpos]->exten[1] = '\0';
05248 }
05249
05250 if (e->ring.complete && (ast_strlen_zero(e->ring.callednum))) {
05251 ast_verb(3, "Going to extension s|1 because of Complete received\n");
05252 pri->pvts[chanpos]->exten[0] = 's';
05253 pri->pvts[chanpos]->exten[1] = '\0';
05254 }
05255
05256
05257 if (((pri->overlapdial & DAHDI_OVERLAPDIAL_INCOMING) && ast_canmatch_extension(NULL, pri->pvts[chanpos]->context, pri->pvts[chanpos]->exten, 1, pri->pvts[chanpos]->cid_num)) ||
05258 ast_exists_extension(NULL, pri->pvts[chanpos]->context, pri->pvts[chanpos]->exten, 1, pri->pvts[chanpos]->cid_num)) {
05259
05260 switch (e->ring.layer1) {
05261 case PRI_LAYER_1_ALAW:
05262 law = SIG_PRI_ALAW;
05263 break;
05264 case PRI_LAYER_1_ULAW:
05265 law = SIG_PRI_ULAW;
05266 break;
05267 default:
05268
05269 law = SIG_PRI_DEFLAW;
05270 break;
05271 }
05272
05273 if (e->ring.complete || !(pri->overlapdial & DAHDI_OVERLAPDIAL_INCOMING)) {
05274
05275 pri->pvts[chanpos]->call_level = SIG_PRI_CALL_LEVEL_PROCEEDING;
05276 pri_proceeding(pri->pri, e->ring.call, PVT_TO_CHANNEL(pri->pvts[chanpos]), 0);
05277 } else if (pri->switchtype == PRI_SWITCH_GR303_TMC) {
05278 pri->pvts[chanpos]->call_level = SIG_PRI_CALL_LEVEL_CONNECT;
05279 pri_answer(pri->pri, e->ring.call, PVT_TO_CHANNEL(pri->pvts[chanpos]), 1);
05280 } else {
05281 pri->pvts[chanpos]->call_level = SIG_PRI_CALL_LEVEL_OVERLAP;
05282 pri_need_more_info(pri->pri, e->ring.call, PVT_TO_CHANNEL(pri->pvts[chanpos]), 1);
05283 }
05284
05285
05286 if (!e->ring.complete
05287 && (pri->overlapdial & DAHDI_OVERLAPDIAL_INCOMING)
05288 && ast_matchmore_extension(NULL, pri->pvts[chanpos]->context, pri->pvts[chanpos]->exten, 1, pri->pvts[chanpos]->cid_num)) {
05289
05290
05291
05292
05293
05294
05295 sig_pri_unlock_private(pri->pvts[chanpos]);
05296 ast_mutex_unlock(&pri->lock);
05297 c = sig_pri_new_ast_channel(pri->pvts[chanpos],
05298 AST_STATE_RESERVED, law, e->ring.ctype,
05299 pri->pvts[chanpos]->exten, NULL);
05300 ast_mutex_lock(&pri->lock);
05301 sig_pri_lock_private(pri->pvts[chanpos]);
05302 if (c) {
05303 #if defined(HAVE_PRI_SUBADDR)
05304 if (e->ring.calling.subaddress.valid) {
05305
05306 sig_pri_lock_owner(pri, chanpos);
05307 sig_pri_set_subaddress(
05308 &pri->pvts[chanpos]->owner->caller.id.subaddress,
05309 &e->ring.calling.subaddress);
05310 if (!e->ring.calling.subaddress.type
05311 && !ast_strlen_zero(
05312 (char *) e->ring.calling.subaddress.data)) {
05313
05314 pbx_builtin_setvar_helper(c, "CALLINGSUBADDR",
05315 (char *) e->ring.calling.subaddress.data);
05316 }
05317 ast_channel_unlock(c);
05318 }
05319 if (e->ring.called_subaddress.valid) {
05320
05321 sig_pri_lock_owner(pri, chanpos);
05322 sig_pri_set_subaddress(
05323 &pri->pvts[chanpos]->owner->dialed.subaddress,
05324 &e->ring.called_subaddress);
05325 if (!e->ring.called_subaddress.type
05326 && !ast_strlen_zero(
05327 (char *) e->ring.called_subaddress.data)) {
05328
05329 pbx_builtin_setvar_helper(c, "CALLEDSUBADDR",
05330 (char *) e->ring.called_subaddress.data);
05331 }
05332 ast_channel_unlock(c);
05333 }
05334 #else
05335 if (!ast_strlen_zero(e->ring.callingsubaddr)) {
05336 pbx_builtin_setvar_helper(c, "CALLINGSUBADDR", e->ring.callingsubaddr);
05337 }
05338 #endif
05339 if (e->ring.ani2 >= 0) {
05340 snprintf(ani2str, sizeof(ani2str), "%d", e->ring.ani2);
05341 pbx_builtin_setvar_helper(c, "ANI2", ani2str);
05342 }
05343
05344 #ifdef SUPPORT_USERUSER
05345 if (!ast_strlen_zero(e->ring.useruserinfo)) {
05346 pbx_builtin_setvar_helper(c, "USERUSERINFO", e->ring.useruserinfo);
05347 }
05348 #endif
05349
05350 snprintf(calledtonstr, sizeof(calledtonstr), "%d", e->ring.calledplan);
05351 pbx_builtin_setvar_helper(c, "CALLEDTON", calledtonstr);
05352 ast_channel_lock(c);
05353 c->dialed.number.plan = e->ring.calledplan;
05354 ast_channel_unlock(c);
05355
05356 if (e->ring.redirectingreason >= 0) {
05357
05358 pbx_builtin_setvar_helper(c, "PRIREDIRECTREASON", redirectingreason2str(e->ring.redirectingreason));
05359 }
05360 #if defined(HAVE_PRI_REVERSE_CHARGE)
05361 pri->pvts[chanpos]->reverse_charging_indication = e->ring.reversecharge;
05362 #endif
05363 #if defined(HAVE_PRI_SETUP_KEYPAD)
05364 ast_copy_string(pri->pvts[chanpos]->keypad_digits,
05365 e->ring.keypad_digits,
05366 sizeof(pri->pvts[chanpos]->keypad_digits));
05367 #endif
05368
05369 sig_pri_handle_subcmds(pri, chanpos, e->e, e->ring.channel,
05370 e->ring.subcmds, e->ring.call);
05371
05372 if (!pri->pvts[chanpos]->digital
05373 && !pri->pvts[chanpos]->no_b_channel) {
05374
05375
05376
05377
05378 pri->pvts[chanpos]->progress = 1;
05379 #ifdef HAVE_PRI_PROG_W_CAUSE
05380 pri_progress_with_cause(pri->pri, e->ring.call,
05381 PVT_TO_CHANNEL(pri->pvts[chanpos]), 1, -1);
05382 #else
05383 pri_progress(pri->pri, e->ring.call,
05384 PVT_TO_CHANNEL(pri->pvts[chanpos]), 1);
05385 #endif
05386 }
05387 }
05388 if (c && !ast_pthread_create_detached(&threadid, NULL, pri_ss_thread, pri->pvts[chanpos])) {
05389 ast_verb(3, "Accepting overlap call from '%s' to '%s' on channel %d/%d, span %d\n",
05390 plancallingnum, S_OR(pri->pvts[chanpos]->exten, "<unspecified>"),
05391 pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset, pri->span);
05392 } else {
05393 ast_log(LOG_WARNING, "Unable to start PBX on channel %d/%d, span %d\n",
05394 pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset, pri->span);
05395 if (c) {
05396
05397 sig_pri_unlock_private(pri->pvts[chanpos]);
05398 ast_mutex_unlock(&pri->lock);
05399 ast_hangup(c);
05400 ast_mutex_lock(&pri->lock);
05401 } else {
05402 pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_SWITCH_CONGESTION);
05403 pri->pvts[chanpos]->call = NULL;
05404 sig_pri_unlock_private(pri->pvts[chanpos]);
05405 sig_pri_span_devstate_changed(pri);
05406 }
05407 break;
05408 }
05409 } else {
05410
05411
05412
05413
05414
05415
05416 sig_pri_unlock_private(pri->pvts[chanpos]);
05417 ast_mutex_unlock(&pri->lock);
05418 c = sig_pri_new_ast_channel(pri->pvts[chanpos],
05419 AST_STATE_RING, law, e->ring.ctype,
05420 pri->pvts[chanpos]->exten, NULL);
05421 ast_mutex_lock(&pri->lock);
05422 sig_pri_lock_private(pri->pvts[chanpos]);
05423 if (c) {
05424
05425
05426
05427
05428
05429
05430
05431
05432 #if defined(HAVE_PRI_SUBADDR)
05433 if (e->ring.calling.subaddress.valid) {
05434
05435 sig_pri_lock_owner(pri, chanpos);
05436 sig_pri_set_subaddress(
05437 &pri->pvts[chanpos]->owner->caller.id.subaddress,
05438 &e->ring.calling.subaddress);
05439 if (!e->ring.calling.subaddress.type
05440 && !ast_strlen_zero(
05441 (char *) e->ring.calling.subaddress.data)) {
05442
05443 pbx_builtin_setvar_helper(c, "CALLINGSUBADDR",
05444 (char *) e->ring.calling.subaddress.data);
05445 }
05446 ast_channel_unlock(c);
05447 }
05448 if (e->ring.called_subaddress.valid) {
05449
05450 sig_pri_lock_owner(pri, chanpos);
05451 sig_pri_set_subaddress(
05452 &pri->pvts[chanpos]->owner->dialed.subaddress,
05453 &e->ring.called_subaddress);
05454 if (!e->ring.called_subaddress.type
05455 && !ast_strlen_zero(
05456 (char *) e->ring.called_subaddress.data)) {
05457
05458 pbx_builtin_setvar_helper(c, "CALLEDSUBADDR",
05459 (char *) e->ring.called_subaddress.data);
05460 }
05461 ast_channel_unlock(c);
05462 }
05463 #else
05464 if (!ast_strlen_zero(e->ring.callingsubaddr)) {
05465 pbx_builtin_setvar_helper(c, "CALLINGSUBADDR", e->ring.callingsubaddr);
05466 }
05467 #endif
05468 if (e->ring.ani2 >= 0) {
05469 snprintf(ani2str, sizeof(ani2str), "%d", e->ring.ani2);
05470 pbx_builtin_setvar_helper(c, "ANI2", ani2str);
05471 }
05472
05473 #ifdef SUPPORT_USERUSER
05474 if (!ast_strlen_zero(e->ring.useruserinfo)) {
05475 pbx_builtin_setvar_helper(c, "USERUSERINFO", e->ring.useruserinfo);
05476 }
05477 #endif
05478
05479 if (e->ring.redirectingreason >= 0) {
05480
05481 pbx_builtin_setvar_helper(c, "PRIREDIRECTREASON", redirectingreason2str(e->ring.redirectingreason));
05482 }
05483 #if defined(HAVE_PRI_REVERSE_CHARGE)
05484 pri->pvts[chanpos]->reverse_charging_indication = e->ring.reversecharge;
05485 #endif
05486 #if defined(HAVE_PRI_SETUP_KEYPAD)
05487 ast_copy_string(pri->pvts[chanpos]->keypad_digits,
05488 e->ring.keypad_digits,
05489 sizeof(pri->pvts[chanpos]->keypad_digits));
05490 #endif
05491
05492 snprintf(calledtonstr, sizeof(calledtonstr), "%d", e->ring.calledplan);
05493 pbx_builtin_setvar_helper(c, "CALLEDTON", calledtonstr);
05494 ast_channel_lock(c);
05495 c->dialed.number.plan = e->ring.calledplan;
05496 ast_channel_unlock(c);
05497
05498 sig_pri_handle_subcmds(pri, chanpos, e->e, e->ring.channel,
05499 e->ring.subcmds, e->ring.call);
05500 }
05501 if (c && !ast_pbx_start(c)) {
05502 ast_verb(3, "Accepting call from '%s' to '%s' on channel %d/%d, span %d\n",
05503 plancallingnum, pri->pvts[chanpos]->exten,
05504 pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset, pri->span);
05505 sig_pri_set_echocanceller(pri->pvts[chanpos], 1);
05506 } else {
05507 ast_log(LOG_WARNING, "Unable to start PBX on channel %d/%d, span %d\n",
05508 pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset, pri->span);
05509 if (c) {
05510
05511 sig_pri_unlock_private(pri->pvts[chanpos]);
05512 ast_mutex_unlock(&pri->lock);
05513 ast_hangup(c);
05514 ast_mutex_lock(&pri->lock);
05515 } else {
05516 pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_SWITCH_CONGESTION);
05517 pri->pvts[chanpos]->call = NULL;
05518 sig_pri_unlock_private(pri->pvts[chanpos]);
05519 sig_pri_span_devstate_changed(pri);
05520 }
05521 break;
05522 }
05523 }
05524 } else {
05525 ast_verb(3,
05526 "Span %d: Extension %s@%s does not exist. Rejecting call from '%s'.\n",
05527 pri->span, pri->pvts[chanpos]->exten, pri->pvts[chanpos]->context,
05528 pri->pvts[chanpos]->cid_num);
05529 pri_hangup(pri->pri, e->ring.call, PRI_CAUSE_UNALLOCATED);
05530 pri->pvts[chanpos]->call = NULL;
05531 pri->pvts[chanpos]->exten[0] = '\0';
05532 sig_pri_unlock_private(pri->pvts[chanpos]);
05533 sig_pri_span_devstate_changed(pri);
05534 break;
05535 }
05536 sig_pri_unlock_private(pri->pvts[chanpos]);
05537 break;
05538 case PRI_EVENT_RINGING:
05539 if (sig_pri_is_cis_call(e->ringing.channel)) {
05540 sig_pri_handle_cis_subcmds(pri, e->e, e->ringing.subcmds,
05541 e->ringing.call);
05542 break;
05543 }
05544 chanpos = pri_find_fixup_principle(pri, e->ringing.channel,
05545 e->ringing.call);
05546 if (chanpos < 0) {
05547 break;
05548 }
05549 sig_pri_lock_private(pri->pvts[chanpos]);
05550
05551 sig_pri_handle_subcmds(pri, chanpos, e->e, e->ringing.channel,
05552 e->ringing.subcmds, e->ringing.call);
05553 sig_pri_cc_generic_check(pri, chanpos, AST_CC_CCNR);
05554 sig_pri_set_echocanceller(pri->pvts[chanpos], 1);
05555 sig_pri_lock_owner(pri, chanpos);
05556 if (pri->pvts[chanpos]->owner) {
05557 ast_setstate(pri->pvts[chanpos]->owner, AST_STATE_RINGING);
05558 ast_channel_unlock(pri->pvts[chanpos]->owner);
05559 }
05560 pri_queue_control(pri, chanpos, AST_CONTROL_RINGING);
05561 if (pri->pvts[chanpos]->call_level < SIG_PRI_CALL_LEVEL_ALERTING) {
05562 pri->pvts[chanpos]->call_level = SIG_PRI_CALL_LEVEL_ALERTING;
05563 }
05564
05565 if (!pri->pvts[chanpos]->progress
05566 && !pri->pvts[chanpos]->no_b_channel
05567 #ifdef PRI_PROGRESS_MASK
05568 && (e->ringing.progressmask
05569 & (PRI_PROG_CALL_NOT_E2E_ISDN | PRI_PROG_INBAND_AVAILABLE))
05570 #else
05571 && e->ringing.progress == 8
05572 #endif
05573 ) {
05574
05575 pri_queue_control(pri, chanpos, AST_CONTROL_PROGRESS);
05576 pri->pvts[chanpos]->progress = 1;
05577 sig_pri_set_dialing(pri->pvts[chanpos], 0);
05578 sig_pri_open_media(pri->pvts[chanpos]);
05579 }
05580
05581 #ifdef SUPPORT_USERUSER
05582 if (!ast_strlen_zero(e->ringing.useruserinfo)) {
05583 struct ast_channel *owner;
05584
05585 sig_pri_lock_owner(pri, chanpos);
05586 owner = pri->pvts[chanpos]->owner;
05587 if (owner) {
05588 pbx_builtin_setvar_helper(owner, "USERUSERINFO",
05589 e->ringing.useruserinfo);
05590 ast_channel_unlock(owner);
05591 }
05592 }
05593 #endif
05594
05595 sig_pri_unlock_private(pri->pvts[chanpos]);
05596 break;
05597 case PRI_EVENT_PROGRESS:
05598 if (sig_pri_is_cis_call(e->proceeding.channel)) {
05599 sig_pri_handle_cis_subcmds(pri, e->e, e->proceeding.subcmds,
05600 e->proceeding.call);
05601 break;
05602 }
05603 chanpos = pri_find_fixup_principle(pri, e->proceeding.channel,
05604 e->proceeding.call);
05605 if (chanpos < 0) {
05606 break;
05607 }
05608 sig_pri_lock_private(pri->pvts[chanpos]);
05609 sig_pri_handle_subcmds(pri, chanpos, e->e, e->proceeding.channel,
05610 e->proceeding.subcmds, e->proceeding.call);
05611
05612 if (e->proceeding.cause > -1) {
05613 ast_verb(3, "PROGRESS with cause code %d received\n", e->proceeding.cause);
05614
05615
05616 if (e->proceeding.cause == AST_CAUSE_USER_BUSY) {
05617 if (pri->pvts[chanpos]->owner) {
05618 ast_verb(3, "PROGRESS with 'user busy' received, signaling AST_CONTROL_BUSY instead of AST_CONTROL_PROGRESS\n");
05619
05620 pri->pvts[chanpos]->owner->hangupcause = e->proceeding.cause;
05621 pri_queue_control(pri, chanpos, AST_CONTROL_BUSY);
05622 }
05623 }
05624 }
05625
05626 if (!pri->pvts[chanpos]->progress
05627 && !pri->pvts[chanpos]->no_b_channel
05628 #ifdef PRI_PROGRESS_MASK
05629 && (e->proceeding.progressmask
05630 & (PRI_PROG_CALL_NOT_E2E_ISDN | PRI_PROG_INBAND_AVAILABLE))
05631 #else
05632 && e->proceeding.progress == 8
05633 #endif
05634 ) {
05635
05636 ast_debug(1,
05637 "Queuing frame from PRI_EVENT_PROGRESS on channel %d/%d span %d\n",
05638 pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset,
05639 pri->span);
05640 pri_queue_control(pri, chanpos, AST_CONTROL_PROGRESS);
05641 pri->pvts[chanpos]->progress = 1;
05642 sig_pri_set_dialing(pri->pvts[chanpos], 0);
05643 sig_pri_open_media(pri->pvts[chanpos]);
05644 }
05645 sig_pri_unlock_private(pri->pvts[chanpos]);
05646 break;
05647 case PRI_EVENT_PROCEEDING:
05648 if (sig_pri_is_cis_call(e->proceeding.channel)) {
05649 sig_pri_handle_cis_subcmds(pri, e->e, e->proceeding.subcmds,
05650 e->proceeding.call);
05651 break;
05652 }
05653 chanpos = pri_find_fixup_principle(pri, e->proceeding.channel,
05654 e->proceeding.call);
05655 if (chanpos < 0) {
05656 break;
05657 }
05658 sig_pri_lock_private(pri->pvts[chanpos]);
05659 sig_pri_handle_subcmds(pri, chanpos, e->e, e->proceeding.channel,
05660 e->proceeding.subcmds, e->proceeding.call);
05661 if (pri->pvts[chanpos]->call_level < SIG_PRI_CALL_LEVEL_PROCEEDING) {
05662 pri->pvts[chanpos]->call_level = SIG_PRI_CALL_LEVEL_PROCEEDING;
05663 ast_debug(1,
05664 "Queuing frame from PRI_EVENT_PROCEEDING on channel %d/%d span %d\n",
05665 pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset,
05666 pri->span);
05667 pri_queue_control(pri, chanpos, AST_CONTROL_PROCEEDING);
05668 }
05669 if (!pri->pvts[chanpos]->progress
05670 && !pri->pvts[chanpos]->no_b_channel
05671 #ifdef PRI_PROGRESS_MASK
05672 && (e->proceeding.progressmask
05673 & (PRI_PROG_CALL_NOT_E2E_ISDN | PRI_PROG_INBAND_AVAILABLE))
05674 #else
05675 && e->proceeding.progress == 8
05676 #endif
05677 ) {
05678
05679 pri_queue_control(pri, chanpos, AST_CONTROL_PROGRESS);
05680 pri->pvts[chanpos]->progress = 1;
05681 sig_pri_open_media(pri->pvts[chanpos]);
05682 }
05683 sig_pri_set_dialing(pri->pvts[chanpos], 0);
05684 sig_pri_unlock_private(pri->pvts[chanpos]);
05685 break;
05686 case PRI_EVENT_FACILITY:
05687 if (!e->facility.call || sig_pri_is_cis_call(e->facility.channel)) {
05688
05689 #if defined(HAVE_PRI_CALL_REROUTING)
05690 sig_pri_handle_cis_subcmds(pri, e->e, e->facility.subcmds,
05691 e->facility.subcall);
05692 #else
05693 sig_pri_handle_cis_subcmds(pri, e->e, e->facility.subcmds,
05694 e->facility.call);
05695 #endif
05696 break;
05697 }
05698 chanpos = pri_find_principle_by_call(pri, e->facility.call);
05699 if (chanpos < 0) {
05700 ast_log(LOG_WARNING, "Span %d: Received facility for unknown call.\n",
05701 pri->span);
05702 break;
05703 }
05704 sig_pri_lock_private(pri->pvts[chanpos]);
05705 #if defined(HAVE_PRI_CALL_REROUTING)
05706 sig_pri_handle_subcmds(pri, chanpos, e->e, e->facility.channel,
05707 e->facility.subcmds, e->facility.subcall);
05708 #else
05709 sig_pri_handle_subcmds(pri, chanpos, e->e, e->facility.channel,
05710 e->facility.subcmds, e->facility.call);
05711 #endif
05712 sig_pri_unlock_private(pri->pvts[chanpos]);
05713 break;
05714 case PRI_EVENT_ANSWER:
05715 if (sig_pri_is_cis_call(e->answer.channel)) {
05716 #if defined(HAVE_PRI_CALL_WAITING)
05717
05718 pri_connect_ack(pri->pri, e->answer.call, 0);
05719 #endif
05720 sig_pri_handle_cis_subcmds(pri, e->e, e->answer.subcmds,
05721 e->answer.call);
05722 break;
05723 }
05724 chanpos = pri_find_fixup_principle(pri, e->answer.channel, e->answer.call);
05725 if (chanpos < 0) {
05726 break;
05727 }
05728 #if defined(HAVE_PRI_CALL_WAITING)
05729 if (pri->pvts[chanpos]->is_call_waiting) {
05730 if (pri->pvts[chanpos]->no_b_channel) {
05731 int new_chanpos;
05732
05733
05734
05735
05736
05737 new_chanpos = pri_find_empty_chan(pri, 1);
05738 if (0 <= new_chanpos) {
05739 new_chanpos = pri_fixup_principle(pri, new_chanpos,
05740 e->answer.call);
05741 }
05742 if (new_chanpos < 0) {
05743
05744
05745
05746
05747 ast_verb(3,
05748 "Span %d: Channel not available for call waiting call.\n",
05749 pri->span);
05750 sig_pri_lock_private(pri->pvts[chanpos]);
05751 sig_pri_handle_subcmds(pri, chanpos, e->e, e->answer.channel,
05752 e->answer.subcmds, e->answer.call);
05753 sig_pri_cc_generic_check(pri, chanpos, AST_CC_CCBS);
05754 sig_pri_lock_owner(pri, chanpos);
05755 if (pri->pvts[chanpos]->owner) {
05756 pri->pvts[chanpos]->owner->hangupcause = PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION;
05757 switch (pri->pvts[chanpos]->owner->_state) {
05758 case AST_STATE_BUSY:
05759 case AST_STATE_UP:
05760 ast_softhangup_nolock(pri->pvts[chanpos]->owner, AST_SOFTHANGUP_DEV);
05761 break;
05762 default:
05763 pri_queue_control(pri, chanpos, AST_CONTROL_CONGESTION);
05764 break;
05765 }
05766 ast_channel_unlock(pri->pvts[chanpos]->owner);
05767 } else {
05768 pri->pvts[chanpos]->is_call_waiting = 0;
05769 ast_atomic_fetchadd_int(&pri->num_call_waiting_calls, -1);
05770 pri_hangup(pri->pri, e->answer.call, PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION);
05771 pri->pvts[chanpos]->call = NULL;
05772 }
05773 sig_pri_unlock_private(pri->pvts[chanpos]);
05774 sig_pri_span_devstate_changed(pri);
05775 break;
05776 }
05777 chanpos = new_chanpos;
05778 }
05779 pri_connect_ack(pri->pri, e->answer.call, PVT_TO_CHANNEL(pri->pvts[chanpos]));
05780 sig_pri_span_devstate_changed(pri);
05781 } else {
05782
05783 pri_connect_ack(pri->pri, e->answer.call, 0);
05784 }
05785 #endif
05786 sig_pri_lock_private(pri->pvts[chanpos]);
05787
05788 #if defined(HAVE_PRI_CALL_WAITING)
05789 if (pri->pvts[chanpos]->is_call_waiting) {
05790 pri->pvts[chanpos]->is_call_waiting = 0;
05791 ast_atomic_fetchadd_int(&pri->num_call_waiting_calls, -1);
05792 }
05793 #endif
05794 sig_pri_handle_subcmds(pri, chanpos, e->e, e->answer.channel,
05795 e->answer.subcmds, e->answer.call);
05796 if (!ast_strlen_zero(pri->pvts[chanpos]->deferred_digits)) {
05797
05798 ast_verb(3,
05799 "Span %d: Channel %d/%d dialing deferred digit string: %s\n",
05800 pri->span, pri->pvts[chanpos]->logicalspan,
05801 pri->pvts[chanpos]->prioffset,
05802 pri->pvts[chanpos]->deferred_digits);
05803 if (pri->pvts[chanpos]->call_level < SIG_PRI_CALL_LEVEL_DEFER_DIAL) {
05804 pri->pvts[chanpos]->call_level = SIG_PRI_CALL_LEVEL_DEFER_DIAL;
05805 }
05806 sig_pri_dial_digits(pri->pvts[chanpos],
05807 pri->pvts[chanpos]->deferred_digits);
05808 } else {
05809 if (pri->pvts[chanpos]->call_level < SIG_PRI_CALL_LEVEL_CONNECT) {
05810 pri->pvts[chanpos]->call_level = SIG_PRI_CALL_LEVEL_CONNECT;
05811 }
05812 sig_pri_open_media(pri->pvts[chanpos]);
05813 pri_queue_control(pri, chanpos, AST_CONTROL_ANSWER);
05814 sig_pri_set_dialing(pri->pvts[chanpos], 0);
05815
05816 sig_pri_set_echocanceller(pri->pvts[chanpos], 1);
05817 }
05818
05819 #ifdef SUPPORT_USERUSER
05820 if (!ast_strlen_zero(e->answer.useruserinfo)) {
05821 struct ast_channel *owner;
05822
05823 sig_pri_lock_owner(pri, chanpos);
05824 owner = pri->pvts[chanpos]->owner;
05825 if (owner) {
05826 pbx_builtin_setvar_helper(owner, "USERUSERINFO",
05827 e->answer.useruserinfo);
05828 ast_channel_unlock(owner);
05829 }
05830 }
05831 #endif
05832
05833 sig_pri_unlock_private(pri->pvts[chanpos]);
05834 break;
05835 #if defined(HAVE_PRI_CALL_WAITING)
05836 case PRI_EVENT_CONNECT_ACK:
05837 if (sig_pri_is_cis_call(e->connect_ack.channel)) {
05838 sig_pri_handle_cis_subcmds(pri, e->e, e->connect_ack.subcmds,
05839 e->connect_ack.call);
05840 break;
05841 }
05842 chanpos = pri_find_fixup_principle(pri, e->connect_ack.channel,
05843 e->connect_ack.call);
05844 if (chanpos < 0) {
05845 break;
05846 }
05847
05848 sig_pri_lock_private(pri->pvts[chanpos]);
05849 sig_pri_handle_subcmds(pri, chanpos, e->e, e->connect_ack.channel,
05850 e->connect_ack.subcmds, e->connect_ack.call);
05851 sig_pri_open_media(pri->pvts[chanpos]);
05852 sig_pri_unlock_private(pri->pvts[chanpos]);
05853 sig_pri_span_devstate_changed(pri);
05854 break;
05855 #endif
05856 case PRI_EVENT_HANGUP:
05857 if (sig_pri_is_cis_call(e->hangup.channel)) {
05858 sig_pri_handle_cis_subcmds(pri, e->e, e->hangup.subcmds,
05859 e->hangup.call);
05860 pri_hangup(pri->pri, e->hangup.call, e->hangup.cause);
05861 break;
05862 }
05863 chanpos = pri_find_principle_by_call(pri, e->hangup.call);
05864 if (chanpos < 0) {
05865
05866
05867
05868
05869 pri_hangup(pri->pri, e->hangup.call, e->hangup.cause);
05870 break;
05871 }
05872 sig_pri_lock_private(pri->pvts[chanpos]);
05873 sig_pri_handle_subcmds(pri, chanpos, e->e, e->hangup.channel,
05874 e->hangup.subcmds, e->hangup.call);
05875 switch (e->hangup.cause) {
05876 case PRI_CAUSE_INVALID_CALL_REFERENCE:
05877
05878
05879
05880
05881 pri_hangup(pri->pri, e->hangup.call, e->hangup.cause);
05882 pri->pvts[chanpos]->call = NULL;
05883 break;
05884 default:
05885 break;
05886 }
05887 if (!pri->pvts[chanpos]->alreadyhungup) {
05888
05889 pri->pvts[chanpos]->alreadyhungup = 1;
05890 switch (e->hangup.cause) {
05891 case PRI_CAUSE_USER_BUSY:
05892 case PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION:
05893 sig_pri_cc_generic_check(pri, chanpos, AST_CC_CCBS);
05894 break;
05895 default:
05896 break;
05897 }
05898 if (pri->pvts[chanpos]->owner) {
05899 int do_hangup = 0;
05900
05901
05902 pri->pvts[chanpos]->owner->hangupcause = e->hangup.cause;
05903 switch (pri->pvts[chanpos]->owner->_state) {
05904 case AST_STATE_BUSY:
05905 case AST_STATE_UP:
05906 do_hangup = 1;
05907 break;
05908 default:
05909 if (!pri->pvts[chanpos]->outgoing) {
05910
05911
05912
05913
05914 do_hangup = 1;
05915 break;
05916 }
05917 switch (e->hangup.cause) {
05918 case PRI_CAUSE_USER_BUSY:
05919 pri_queue_control(pri, chanpos, AST_CONTROL_BUSY);
05920 break;
05921 case PRI_CAUSE_CALL_REJECTED:
05922 case PRI_CAUSE_NETWORK_OUT_OF_ORDER:
05923 case PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION:
05924 case PRI_CAUSE_SWITCH_CONGESTION:
05925 case PRI_CAUSE_DESTINATION_OUT_OF_ORDER:
05926 case PRI_CAUSE_NORMAL_TEMPORARY_FAILURE:
05927 pri_queue_control(pri, chanpos, AST_CONTROL_CONGESTION);
05928 break;
05929 default:
05930 do_hangup = 1;
05931 break;
05932 }
05933 break;
05934 }
05935
05936 if (do_hangup) {
05937 #if defined(HAVE_PRI_AOC_EVENTS)
05938 if (detect_aoc_e_subcmd(e->hangup.subcmds)) {
05939
05940
05941 pri_queue_control(pri, chanpos, AST_CONTROL_HANGUP);
05942 } else {
05943 pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
05944 }
05945 #else
05946 pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
05947 #endif
05948 }
05949 } else {
05950
05951
05952
05953
05954 pri_hangup(pri->pri, pri->pvts[chanpos]->call, e->hangup.cause);
05955 pri->pvts[chanpos]->call = NULL;
05956 }
05957 ast_verb(3, "Span %d: Channel %d/%d got hangup, cause %d\n",
05958 pri->span, pri->pvts[chanpos]->logicalspan,
05959 pri->pvts[chanpos]->prioffset, e->hangup.cause);
05960 } else {
05961
05962 pri_hangup(pri->pri, pri->pvts[chanpos]->call, e->hangup.cause);
05963 pri->pvts[chanpos]->call = NULL;
05964 }
05965 #if defined(FORCE_RESTART_UNAVAIL_CHANS)
05966 if (e->hangup.cause == PRI_CAUSE_REQUESTED_CHAN_UNAVAIL
05967 && pri->sig != SIG_BRI_PTMP && !pri->resetting
05968 && pri->pvts[chanpos]->resetting == SIG_PRI_RESET_IDLE) {
05969 ast_verb(3,
05970 "Span %d: Forcing restart of channel %d/%d since channel reported in use\n",
05971 pri->span, pri->pvts[chanpos]->logicalspan,
05972 pri->pvts[chanpos]->prioffset);
05973 pri->pvts[chanpos]->resetting = SIG_PRI_RESET_ACTIVE;
05974 pri_reset(pri->pri, PVT_TO_CHANNEL(pri->pvts[chanpos]));
05975 }
05976 #endif
05977 if (e->hangup.aoc_units > -1)
05978 ast_verb(3, "Channel %d/%d, span %d received AOC-E charging %d unit%s\n",
05979 pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset, pri->span, (int)e->hangup.aoc_units, (e->hangup.aoc_units == 1) ? "" : "s");
05980
05981 #ifdef SUPPORT_USERUSER
05982 if (!ast_strlen_zero(e->hangup.useruserinfo)) {
05983 struct ast_channel *owner;
05984
05985 sig_pri_lock_owner(pri, chanpos);
05986 owner = pri->pvts[chanpos]->owner;
05987 if (owner) {
05988 pbx_builtin_setvar_helper(owner, "USERUSERINFO",
05989 e->hangup.useruserinfo);
05990 ast_channel_unlock(owner);
05991 }
05992 }
05993 #endif
05994
05995 sig_pri_unlock_private(pri->pvts[chanpos]);
05996 sig_pri_span_devstate_changed(pri);
05997 break;
05998 case PRI_EVENT_HANGUP_REQ:
05999 if (sig_pri_is_cis_call(e->hangup.channel)) {
06000 sig_pri_handle_cis_subcmds(pri, e->e, e->hangup.subcmds,
06001 e->hangup.call);
06002 pri_hangup(pri->pri, e->hangup.call, e->hangup.cause);
06003 break;
06004 }
06005 chanpos = pri_find_principle_by_call(pri, e->hangup.call);
06006 if (chanpos < 0) {
06007
06008
06009
06010
06011 pri_hangup(pri->pri, e->hangup.call, e->hangup.cause);
06012 break;
06013 }
06014 sig_pri_lock_private(pri->pvts[chanpos]);
06015 sig_pri_handle_subcmds(pri, chanpos, e->e, e->hangup.channel,
06016 e->hangup.subcmds, e->hangup.call);
06017 #if defined(HAVE_PRI_CALL_HOLD)
06018 if (e->hangup.call_active && e->hangup.call_held
06019 && pri->hold_disconnect_transfer) {
06020
06021 sig_pri_unlock_private(pri->pvts[chanpos]);
06022 if (!sig_pri_attempt_transfer(pri, e->hangup.call_held, 1,
06023 e->hangup.call_active, 0, NULL, NULL)) {
06024 break;
06025 }
06026 sig_pri_lock_private(pri->pvts[chanpos]);
06027 }
06028 #endif
06029 switch (e->hangup.cause) {
06030 case PRI_CAUSE_USER_BUSY:
06031 case PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION:
06032 sig_pri_cc_generic_check(pri, chanpos, AST_CC_CCBS);
06033 break;
06034 case PRI_CAUSE_INVALID_CALL_REFERENCE:
06035
06036
06037
06038
06039
06040
06041 pri_hangup(pri->pri, e->hangup.call, e->hangup.cause);
06042 pri->pvts[chanpos]->call = NULL;
06043 break;
06044 default:
06045 break;
06046 }
06047 if (pri->pvts[chanpos]->owner) {
06048 int do_hangup = 0;
06049
06050 pri->pvts[chanpos]->owner->hangupcause = e->hangup.cause;
06051 switch (pri->pvts[chanpos]->owner->_state) {
06052 case AST_STATE_BUSY:
06053 case AST_STATE_UP:
06054 do_hangup = 1;
06055 break;
06056 default:
06057 if (!pri->pvts[chanpos]->outgoing) {
06058
06059
06060
06061
06062 do_hangup = 1;
06063 break;
06064 }
06065 switch (e->hangup.cause) {
06066 case PRI_CAUSE_USER_BUSY:
06067 pri_queue_control(pri, chanpos, AST_CONTROL_BUSY);
06068 break;
06069 case PRI_CAUSE_CALL_REJECTED:
06070 case PRI_CAUSE_NETWORK_OUT_OF_ORDER:
06071 case PRI_CAUSE_NORMAL_CIRCUIT_CONGESTION:
06072 case PRI_CAUSE_SWITCH_CONGESTION:
06073 case PRI_CAUSE_DESTINATION_OUT_OF_ORDER:
06074 case PRI_CAUSE_NORMAL_TEMPORARY_FAILURE:
06075 pri_queue_control(pri, chanpos, AST_CONTROL_CONGESTION);
06076 break;
06077 default:
06078 do_hangup = 1;
06079 break;
06080 }
06081 break;
06082 }
06083
06084 if (do_hangup) {
06085 #if defined(HAVE_PRI_AOC_EVENTS)
06086 if (!pri->pvts[chanpos]->holding_aoce
06087 && pri->aoce_delayhangup
06088 && ast_bridged_channel(pri->pvts[chanpos]->owner)) {
06089 sig_pri_send_aoce_termination_request(pri, chanpos,
06090 pri_get_timer(pri->pri, PRI_TIMER_T305) / 2);
06091 } else if (detect_aoc_e_subcmd(e->hangup.subcmds)) {
06092
06093
06094 pri_queue_control(pri, chanpos, AST_CONTROL_HANGUP);
06095 } else {
06096 pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
06097 }
06098 #else
06099 pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
06100 #endif
06101 }
06102 ast_verb(3, "Span %d: Channel %d/%d got hangup request, cause %d\n",
06103 pri->span, pri->pvts[chanpos]->logicalspan,
06104 pri->pvts[chanpos]->prioffset, e->hangup.cause);
06105 } else {
06106
06107
06108
06109
06110 pri_hangup(pri->pri, pri->pvts[chanpos]->call, e->hangup.cause);
06111 pri->pvts[chanpos]->call = NULL;
06112 }
06113 #if defined(FORCE_RESTART_UNAVAIL_CHANS)
06114 if (e->hangup.cause == PRI_CAUSE_REQUESTED_CHAN_UNAVAIL
06115 && pri->sig != SIG_BRI_PTMP && !pri->resetting
06116 && pri->pvts[chanpos]->resetting == SIG_PRI_RESET_IDLE) {
06117 ast_verb(3,
06118 "Span %d: Forcing restart of channel %d/%d since channel reported in use\n",
06119 pri->span, pri->pvts[chanpos]->logicalspan,
06120 pri->pvts[chanpos]->prioffset);
06121 pri->pvts[chanpos]->resetting = SIG_PRI_RESET_ACTIVE;
06122 pri_reset(pri->pri, PVT_TO_CHANNEL(pri->pvts[chanpos]));
06123 }
06124 #endif
06125
06126 #ifdef SUPPORT_USERUSER
06127 if (!ast_strlen_zero(e->hangup.useruserinfo)) {
06128 struct ast_channel *owner;
06129
06130 sig_pri_lock_owner(pri, chanpos);
06131 owner = pri->pvts[chanpos]->owner;
06132 if (owner) {
06133 pbx_builtin_setvar_helper(owner, "USERUSERINFO",
06134 e->hangup.useruserinfo);
06135 ast_channel_unlock(owner);
06136 }
06137 }
06138 #endif
06139
06140 sig_pri_unlock_private(pri->pvts[chanpos]);
06141 sig_pri_span_devstate_changed(pri);
06142 break;
06143 case PRI_EVENT_HANGUP_ACK:
06144 if (sig_pri_is_cis_call(e->hangup.channel)) {
06145 sig_pri_handle_cis_subcmds(pri, e->e, e->hangup.subcmds,
06146 e->hangup.call);
06147 break;
06148 }
06149 chanpos = pri_find_principle_by_call(pri, e->hangup.call);
06150 if (chanpos < 0) {
06151 break;
06152 }
06153 sig_pri_lock_private(pri->pvts[chanpos]);
06154 pri->pvts[chanpos]->call = NULL;
06155 if (pri->pvts[chanpos]->owner) {
06156 ast_verb(3, "Span %d: Channel %d/%d got hangup ACK\n", pri->span,
06157 pri->pvts[chanpos]->logicalspan, pri->pvts[chanpos]->prioffset);
06158 }
06159 #ifdef SUPPORT_USERUSER
06160 if (!ast_strlen_zero(e->hangup.useruserinfo)) {
06161 struct ast_channel *owner;
06162
06163 sig_pri_lock_owner(pri, chanpos);
06164 owner = pri->pvts[chanpos]->owner;
06165 if (owner) {
06166 pbx_builtin_setvar_helper(owner, "USERUSERINFO",
06167 e->hangup.useruserinfo);
06168 ast_channel_unlock(owner);
06169 }
06170 }
06171 #endif
06172 sig_pri_unlock_private(pri->pvts[chanpos]);
06173 sig_pri_span_devstate_changed(pri);
06174 break;
06175 case PRI_EVENT_CONFIG_ERR:
06176 ast_log(LOG_WARNING, "PRI Error on span %d: %s\n", pri->span, e->err.err);
06177 break;
06178 case PRI_EVENT_RESTART_ACK:
06179 chanpos = pri_find_principle(pri, e->restartack.channel, NULL);
06180 if (chanpos < 0) {
06181
06182
06183
06184 for (x = 0; x < pri->numchans; x++) {
06185 if (pri->pvts[x]
06186 && pri->pvts[x]->resetting != SIG_PRI_RESET_IDLE) {
06187 chanpos = x;
06188 sig_pri_lock_private(pri->pvts[chanpos]);
06189 ast_debug(1,
06190 "Span %d: Assuming restart ack is for channel %d/%d\n",
06191 pri->span, pri->pvts[chanpos]->logicalspan,
06192 pri->pvts[chanpos]->prioffset);
06193 if (pri->pvts[chanpos]->owner) {
06194 ast_log(LOG_WARNING,
06195 "Span %d: Got restart ack on channel %d/%d with owner\n",
06196 pri->span, pri->pvts[chanpos]->logicalspan,
06197 pri->pvts[chanpos]->prioffset);
06198 pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
06199 }
06200 pri->pvts[chanpos]->resetting = SIG_PRI_RESET_IDLE;
06201 ast_verb(3,
06202 "Span %d: Channel %d/%d successfully restarted\n",
06203 pri->span, pri->pvts[chanpos]->logicalspan,
06204 pri->pvts[chanpos]->prioffset);
06205 sig_pri_unlock_private(pri->pvts[chanpos]);
06206 if (pri->resetting)
06207 pri_check_restart(pri);
06208 break;
06209 }
06210 }
06211 if (chanpos < 0) {
06212 ast_log(LOG_WARNING,
06213 "Span %d: Restart ACK on strange channel %d/%d\n",
06214 pri->span, PRI_SPAN(e->restartack.channel),
06215 PRI_CHANNEL(e->restartack.channel));
06216 }
06217 } else {
06218 sig_pri_lock_private(pri->pvts[chanpos]);
06219 if (pri->pvts[chanpos]->resetting == SIG_PRI_RESET_IDLE) {
06220
06221 ast_debug(1,
06222 "Span %d: Unexpected or late restart ack on channel %d/%d (Ignoring)\n",
06223 pri->span, pri->pvts[chanpos]->logicalspan,
06224 pri->pvts[chanpos]->prioffset);
06225 sig_pri_unlock_private(pri->pvts[chanpos]);
06226 break;
06227 }
06228 if (pri->pvts[chanpos]->owner) {
06229 ast_log(LOG_WARNING,
06230 "Span %d: Got restart ack on channel %d/%d with owner\n",
06231 pri->span, pri->pvts[chanpos]->logicalspan,
06232 pri->pvts[chanpos]->prioffset);
06233 pri->pvts[chanpos]->owner->_softhangup |= AST_SOFTHANGUP_DEV;
06234 }
06235 pri->pvts[chanpos]->resetting = SIG_PRI_RESET_IDLE;
06236 ast_verb(3,
06237 "Span %d: Channel %d/%d successfully restarted\n",
06238 pri->span, pri->pvts[chanpos]->logicalspan,
06239 pri->pvts[chanpos]->prioffset);
06240 sig_pri_unlock_private(pri->pvts[chanpos]);
06241 if (pri->resetting)
06242 pri_check_restart(pri);
06243 }
06244 break;
06245 case PRI_EVENT_SETUP_ACK:
06246 if (sig_pri_is_cis_call(e->setup_ack.channel)) {
06247 sig_pri_handle_cis_subcmds(pri, e->e, e->setup_ack.subcmds,
06248 e->setup_ack.call);
06249 break;
06250 }
06251 chanpos = pri_find_fixup_principle(pri, e->setup_ack.channel,
06252 e->setup_ack.call);
06253 if (chanpos < 0) {
06254 break;
06255 }
06256 sig_pri_lock_private(pri->pvts[chanpos]);
06257 sig_pri_handle_subcmds(pri, chanpos, e->e, e->setup_ack.channel,
06258 e->setup_ack.subcmds, e->setup_ack.call);
06259 if (pri->pvts[chanpos]->call_level < SIG_PRI_CALL_LEVEL_OVERLAP) {
06260 pri->pvts[chanpos]->call_level = SIG_PRI_CALL_LEVEL_OVERLAP;
06261 }
06262
06263
06264 len = strlen(pri->pvts[chanpos]->dialdest);
06265 for (x = 0; x < len; ++x) {
06266 ast_debug(1, "Sending pending digit '%c'\n", pri->pvts[chanpos]->dialdest[x]);
06267 pri_information(pri->pri, pri->pvts[chanpos]->call,
06268 pri->pvts[chanpos]->dialdest[x]);
06269 }
06270
06271 if (!pri->pvts[chanpos]->progress
06272 && (pri->overlapdial & DAHDI_OVERLAPDIAL_OUTGOING)
06273 && !pri->pvts[chanpos]->digital
06274 && !pri->pvts[chanpos]->no_b_channel) {
06275
06276
06277
06278
06279 pri_queue_control(pri, chanpos, AST_CONTROL_PROGRESS);
06280 pri->pvts[chanpos]->progress = 1;
06281 sig_pri_set_dialing(pri->pvts[chanpos], 0);
06282 sig_pri_open_media(pri->pvts[chanpos]);
06283 }
06284 sig_pri_unlock_private(pri->pvts[chanpos]);
06285 break;
06286 case PRI_EVENT_NOTIFY:
06287 if (sig_pri_is_cis_call(e->notify.channel)) {
06288 #if defined(HAVE_PRI_CALL_HOLD)
06289 sig_pri_handle_cis_subcmds(pri, e->e, e->notify.subcmds,
06290 e->notify.call);
06291 #else
06292 sig_pri_handle_cis_subcmds(pri, e->e, e->notify.subcmds, NULL);
06293 #endif
06294 break;
06295 }
06296 #if defined(HAVE_PRI_CALL_HOLD)
06297 chanpos = pri_find_principle_by_call(pri, e->notify.call);
06298 if (chanpos < 0) {
06299 ast_log(LOG_WARNING, "Span %d: Received NOTIFY for unknown call.\n",
06300 pri->span);
06301 break;
06302 }
06303 #else
06304
06305
06306
06307
06308
06309 chanpos = pri_find_principle(pri, e->notify.channel, NULL);
06310 if (chanpos < 0) {
06311 ast_log(LOG_WARNING, "Received NOTIFY on unconfigured channel %d/%d span %d\n",
06312 PRI_SPAN(e->notify.channel), PRI_CHANNEL(e->notify.channel), pri->span);
06313 break;
06314 }
06315 #endif
06316 sig_pri_lock_private(pri->pvts[chanpos]);
06317 #if defined(HAVE_PRI_CALL_HOLD)
06318 sig_pri_handle_subcmds(pri, chanpos, e->e, e->notify.channel,
06319 e->notify.subcmds, e->notify.call);
06320 #else
06321 sig_pri_handle_subcmds(pri, chanpos, e->e, e->notify.channel,
06322 e->notify.subcmds, NULL);
06323 #endif
06324 switch (e->notify.info) {
06325 case PRI_NOTIFY_REMOTE_HOLD:
06326 if (!pri->discardremoteholdretrieval) {
06327 pri_queue_control(pri, chanpos, AST_CONTROL_HOLD);
06328 }
06329 break;
06330 case PRI_NOTIFY_REMOTE_RETRIEVAL:
06331 if (!pri->discardremoteholdretrieval) {
06332 pri_queue_control(pri, chanpos, AST_CONTROL_UNHOLD);
06333 }
06334 break;
06335 }
06336 sig_pri_unlock_private(pri->pvts[chanpos]);
06337 break;
06338 #if defined(HAVE_PRI_CALL_HOLD)
06339 case PRI_EVENT_HOLD:
06340
06341 if (sig_pri_handle_hold(pri, e)) {
06342 pri_hold_rej(pri->pri, e->hold.call,
06343 PRI_CAUSE_RESOURCE_UNAVAIL_UNSPECIFIED);
06344 } else {
06345 pri_hold_ack(pri->pri, e->hold.call);
06346 }
06347 break;
06348 #endif
06349 #if defined(HAVE_PRI_CALL_HOLD)
06350 case PRI_EVENT_HOLD_ACK:
06351 ast_debug(1, "Event: HOLD_ACK\n");
06352 break;
06353 #endif
06354 #if defined(HAVE_PRI_CALL_HOLD)
06355 case PRI_EVENT_HOLD_REJ:
06356 ast_debug(1, "Event: HOLD_REJ\n");
06357 break;
06358 #endif
06359 #if defined(HAVE_PRI_CALL_HOLD)
06360 case PRI_EVENT_RETRIEVE:
06361
06362 sig_pri_handle_retrieve(pri, e);
06363 break;
06364 #endif
06365 #if defined(HAVE_PRI_CALL_HOLD)
06366 case PRI_EVENT_RETRIEVE_ACK:
06367 ast_debug(1, "Event: RETRIEVE_ACK\n");
06368 break;
06369 #endif
06370 #if defined(HAVE_PRI_CALL_HOLD)
06371 case PRI_EVENT_RETRIEVE_REJ:
06372 ast_debug(1, "Event: RETRIEVE_REJ\n");
06373 break;
06374 #endif
06375 default:
06376 ast_debug(1, "Event: %d\n", e->e);
06377 break;
06378 }
06379 }
06380 ast_mutex_unlock(&pri->lock);
06381 }
06382
06383 return NULL;
06384 }
06385
06386 void sig_pri_init_pri(struct sig_pri_span *pri)
06387 {
06388 int i;
06389
06390 memset(pri, 0, sizeof(*pri));
06391
06392 ast_mutex_init(&pri->lock);
06393
06394 pri->master = AST_PTHREADT_NULL;
06395 for (i = 0; i < SIG_PRI_NUM_DCHANS; i++)
06396 pri->fds[i] = -1;
06397 }
06398
06399 int sig_pri_hangup(struct sig_pri_chan *p, struct ast_channel *ast)
06400 {
06401 ast_debug(1, "%s %d\n", __FUNCTION__, p->channel);
06402 if (!ast->tech_pvt) {
06403 ast_log(LOG_WARNING, "Asked to hangup channel not connected\n");
06404 return 0;
06405 }
06406
06407 sig_pri_set_outgoing(p, 0);
06408 sig_pri_set_digital(p, 0);
06409 #if defined(HAVE_PRI_CALL_WAITING)
06410 if (p->is_call_waiting) {
06411 p->is_call_waiting = 0;
06412 ast_atomic_fetchadd_int(&p->pri->num_call_waiting_calls, -1);
06413 }
06414 #endif
06415 p->call_level = SIG_PRI_CALL_LEVEL_IDLE;
06416 p->progress = 0;
06417 p->cid_num[0] = '\0';
06418 p->cid_subaddr[0] = '\0';
06419 p->cid_name[0] = '\0';
06420 p->user_tag[0] = '\0';
06421 p->exten[0] = '\0';
06422 sig_pri_set_dialing(p, 0);
06423
06424
06425 pri_grab(p, p->pri);
06426 if (p->call) {
06427 #if defined(SUPPORT_USERUSER)
06428 const char *useruser = pbx_builtin_getvar_helper(ast, "USERUSERINFO");
06429
06430 if (!ast_strlen_zero(useruser)) {
06431 pri_call_set_useruser(p->call, useruser);
06432 }
06433 #endif
06434
06435 #if defined(HAVE_PRI_AOC_EVENTS)
06436 if (p->holding_aoce) {
06437 pri_aoc_e_send(p->pri->pri, p->call, &p->aoc_e);
06438 }
06439 #endif
06440
06441 if (p->alreadyhungup) {
06442 ast_debug(1, "Already hungup... Calling hangup once, and clearing call\n");
06443
06444 pri_hangup(p->pri->pri, p->call, -1);
06445 p->call = NULL;
06446 } else {
06447 const char *cause = pbx_builtin_getvar_helper(ast,"PRI_CAUSE");
06448 int icause = ast->hangupcause ? ast->hangupcause : -1;
06449
06450 p->alreadyhungup = 1;
06451 if (!ast_strlen_zero(cause)) {
06452 if (atoi(cause)) {
06453 icause = atoi(cause);
06454 }
06455 }
06456 ast_debug(1,
06457 "Not yet hungup... Calling hangup with cause %d, and clearing call\n",
06458 icause);
06459
06460 pri_hangup(p->pri->pri, p->call, icause);
06461 }
06462 }
06463 #if defined(HAVE_PRI_AOC_EVENTS)
06464 p->aoc_s_request_invoke_id_valid = 0;
06465 p->holding_aoce = 0;
06466 p->waiting_for_aoce = 0;
06467 #endif
06468
06469 p->allocated = 0;
06470 p->owner = NULL;
06471
06472 sig_pri_span_devstate_changed(p->pri);
06473 pri_rel(p->pri);
06474 return 0;
06475 }
06476
06477
06478
06479
06480
06481
06482
06483
06484
06485
06486
06487
06488
06489
06490 void sig_pri_extract_called_num_subaddr(struct sig_pri_chan *p, const char *rdest, char *called, size_t called_buff_size)
06491 {
06492 char *dial;
06493 char *number;
06494 char *subaddr;
06495 AST_DECLARE_APP_ARGS(args,
06496 AST_APP_ARG(group);
06497 AST_APP_ARG(ext);
06498
06499 AST_APP_ARG(other);
06500 );
06501
06502
06503 dial = ast_strdupa(rdest);
06504 AST_NONSTANDARD_APP_ARGS(args, dial, '/');
06505
06506 number = args.ext;
06507 if (!number) {
06508 number = "";
06509 }
06510
06511
06512 subaddr = strchr(number, ':');
06513 if (subaddr) {
06514 *subaddr++ = '\0';
06515
06516
06517 switch (*subaddr) {
06518 case 'U':
06519 case 'u':
06520 case 'N':
06521 case 'n':
06522 ++subaddr;
06523 break;
06524 default:
06525 break;
06526 }
06527 }
06528
06529
06530 if (strlen(number) < p->stripmsd) {
06531 number = "";
06532 } else {
06533 char *deferred;
06534
06535 number += p->stripmsd;
06536 deferred = strchr(number, 'w');
06537 if (deferred) {
06538
06539 *deferred = '\0';
06540 }
06541 while (isalpha(*number)) {
06542 ++number;
06543 }
06544 }
06545
06546
06547 if (ast_strlen_zero(subaddr)) {
06548
06549 snprintf(called, called_buff_size, "%s", number);
06550 } else {
06551
06552 snprintf(called, called_buff_size, "%s:%s", number, subaddr);
06553 }
06554 }
06555
06556 enum SIG_PRI_CALL_OPT_FLAGS {
06557 OPT_KEYPAD = (1 << 0),
06558 OPT_REVERSE_CHARGE = (1 << 1),
06559 OPT_AOC_REQUEST = (1 << 2),
06560 };
06561 enum SIG_PRI_CALL_OPT_ARGS {
06562 OPT_ARG_KEYPAD = 0,
06563 OPT_ARG_AOC_REQUEST,
06564
06565
06566 OPT_ARG_ARRAY_SIZE,
06567 };
06568
06569 AST_APP_OPTIONS(sig_pri_call_opts, BEGIN_OPTIONS
06570 AST_APP_OPTION_ARG('K', OPT_KEYPAD, OPT_ARG_KEYPAD),
06571 AST_APP_OPTION('R', OPT_REVERSE_CHARGE),
06572 AST_APP_OPTION_ARG('A', OPT_AOC_REQUEST, OPT_ARG_AOC_REQUEST),
06573 END_OPTIONS);
06574
06575
06576 int sig_pri_call(struct sig_pri_chan *p, struct ast_channel *ast, char *rdest, int timeout, int layer1)
06577 {
06578 char dest[256];
06579 struct ast_party_subaddress dialed_subaddress;
06580 struct pri_sr *sr;
06581 char *c, *l, *n, *s;
06582 #ifdef SUPPORT_USERUSER
06583 const char *useruser;
06584 #endif
06585 int core_id;
06586 int pridialplan;
06587 int dp_strip;
06588 int prilocaldialplan;
06589 int ldp_strip;
06590 int exclusive;
06591 #if defined(HAVE_PRI_SETUP_KEYPAD)
06592 const char *keypad;
06593 #endif
06594 AST_DECLARE_APP_ARGS(args,
06595 AST_APP_ARG(group);
06596 AST_APP_ARG(ext);
06597 AST_APP_ARG(opts);
06598 AST_APP_ARG(other);
06599 );
06600 struct ast_flags opts;
06601 char *opt_args[OPT_ARG_ARRAY_SIZE];
06602
06603 ast_log(LOG_DEBUG, "CALLER NAME: %s NUM: %s\n",
06604 S_COR(ast->connected.id.name.valid, ast->connected.id.name.str, ""),
06605 S_COR(ast->connected.id.number.valid, ast->connected.id.number.str, ""));
06606
06607 if (!p->pri) {
06608 ast_log(LOG_ERROR, "Could not find pri on channel %d\n", p->channel);
06609 return -1;
06610 }
06611
06612 if ((ast->_state != AST_STATE_DOWN) && (ast->_state != AST_STATE_RESERVED)) {
06613 ast_log(LOG_WARNING, "sig_pri_call called on %s, neither down nor reserved\n", ast->name);
06614 return -1;
06615 }
06616
06617 p->dialdest[0] = '\0';
06618 sig_pri_set_outgoing(p, 1);
06619
06620 ast_copy_string(dest, rdest, sizeof(dest));
06621 AST_NONSTANDARD_APP_ARGS(args, dest, '/');
06622 if (ast_app_parse_options(sig_pri_call_opts, &opts, opt_args, args.opts)) {
06623
06624 return -1;
06625 }
06626
06627 c = args.ext;
06628 if (!c) {
06629 c = "";
06630 }
06631
06632
06633 ast_party_subaddress_init(&dialed_subaddress);
06634 s = strchr(c, ':');
06635 if (s) {
06636 *s = '\0';
06637 s++;
06638
06639
06640
06641
06642 switch (*s) {
06643 case 'U':
06644 case 'u':
06645 s++;
06646 dialed_subaddress.type = 2;
06647 break;
06648 case 'N':
06649 case 'n':
06650 s++;
06651
06652 break;
06653 }
06654 dialed_subaddress.str = s;
06655 dialed_subaddress.valid = 1;
06656 }
06657
06658 l = NULL;
06659 n = NULL;
06660 if (!p->hidecallerid) {
06661 if (ast->connected.id.number.valid) {
06662
06663
06664
06665
06666 for (l = ast->connected.id.number.str; l && *l; l++) {
06667 if (strchr("0123456789", *l)) {
06668 l = ast->connected.id.number.str;
06669 break;
06670 }
06671 }
06672 } else {
06673 l = NULL;
06674 }
06675 if (!p->hidecalleridname) {
06676 n = ast->connected.id.name.valid ? ast->connected.id.name.str : NULL;
06677 }
06678 }
06679
06680 if (strlen(c) < p->stripmsd) {
06681 ast_log(LOG_WARNING, "Number '%s' is shorter than stripmsd (%d)\n", c, p->stripmsd);
06682 return -1;
06683 }
06684
06685
06686 s = strchr(c + p->stripmsd, 'w');
06687 if (s) {
06688 *s++ = '\0';
06689 ast_copy_string(p->deferred_digits, s, sizeof(p->deferred_digits));
06690
06691
06692
06693
06694
06695 } else {
06696 p->deferred_digits[0] = '\0';
06697 }
06698
06699 pri_grab(p, p->pri);
06700 if (!(p->call = pri_new_call(p->pri->pri))) {
06701 ast_log(LOG_WARNING, "Unable to create call on channel %d\n", p->channel);
06702 pri_rel(p->pri);
06703 return -1;
06704 }
06705 if (!(sr = pri_sr_new())) {
06706 ast_log(LOG_WARNING, "Failed to allocate setup request on channel %d\n",
06707 p->channel);
06708 pri_destroycall(p->pri->pri, p->call);
06709 p->call = NULL;
06710 pri_rel(p->pri);
06711 return -1;
06712 }
06713
06714 sig_pri_set_digital(p, IS_DIGITAL(ast->transfercapability));
06715
06716 #if defined(HAVE_PRI_CALL_WAITING)
06717 if (p->is_call_waiting) {
06718
06719
06720
06721
06722 pri_sr_set_channel(sr, 0, 0, 1);
06723 } else
06724 #endif
06725 {
06726
06727 if (p->priexclusive || p->pri->nodetype == PRI_NETWORK) {
06728 exclusive = 1;
06729 } else {
06730 exclusive = 0;
06731 }
06732 pri_sr_set_channel(sr, PVT_TO_CHANNEL(p), exclusive, 1);
06733 }
06734
06735 pri_sr_set_bearer(sr, p->digital ? PRI_TRANS_CAP_DIGITAL : ast->transfercapability,
06736 (p->digital ? -1 : layer1));
06737
06738 if (p->pri->facilityenable)
06739 pri_facility_enable(p->pri->pri);
06740
06741 ast_verb(3, "Requested transfer capability: 0x%.2x - %s\n", ast->transfercapability, ast_transfercapability2str(ast->transfercapability));
06742 dp_strip = 0;
06743 pridialplan = p->pri->dialplan - 1;
06744 if (pridialplan == -2 || pridialplan == -3) {
06745 if (strncmp(c + p->stripmsd, p->pri->internationalprefix, strlen(p->pri->internationalprefix)) == 0) {
06746 if (pridialplan == -2) {
06747 dp_strip = strlen(p->pri->internationalprefix);
06748 }
06749 pridialplan = PRI_INTERNATIONAL_ISDN;
06750 } else if (strncmp(c + p->stripmsd, p->pri->nationalprefix, strlen(p->pri->nationalprefix)) == 0) {
06751 if (pridialplan == -2) {
06752 dp_strip = strlen(p->pri->nationalprefix);
06753 }
06754 pridialplan = PRI_NATIONAL_ISDN;
06755 } else {
06756 pridialplan = PRI_LOCAL_ISDN;
06757 }
06758 }
06759 while (c[p->stripmsd] > '9' && c[p->stripmsd] != '*' && c[p->stripmsd] != '#') {
06760 switch (c[p->stripmsd]) {
06761 case 'U':
06762 pridialplan = (PRI_TON_UNKNOWN << 4) | (pridialplan & 0xf);
06763 break;
06764 case 'I':
06765 pridialplan = (PRI_TON_INTERNATIONAL << 4) | (pridialplan & 0xf);
06766 break;
06767 case 'N':
06768 pridialplan = (PRI_TON_NATIONAL << 4) | (pridialplan & 0xf);
06769 break;
06770 case 'L':
06771 pridialplan = (PRI_TON_NET_SPECIFIC << 4) | (pridialplan & 0xf);
06772 break;
06773 case 'S':
06774 pridialplan = (PRI_TON_SUBSCRIBER << 4) | (pridialplan & 0xf);
06775 break;
06776 case 'V':
06777 pridialplan = (PRI_TON_ABBREVIATED << 4) | (pridialplan & 0xf);
06778 break;
06779 case 'R':
06780 pridialplan = (PRI_TON_RESERVED << 4) | (pridialplan & 0xf);
06781 break;
06782 case 'u':
06783 pridialplan = PRI_NPI_UNKNOWN | (pridialplan & 0xf0);
06784 break;
06785 case 'e':
06786 pridialplan = PRI_NPI_E163_E164 | (pridialplan & 0xf0);
06787 break;
06788 case 'x':
06789 pridialplan = PRI_NPI_X121 | (pridialplan & 0xf0);
06790 break;
06791 case 'f':
06792 pridialplan = PRI_NPI_F69 | (pridialplan & 0xf0);
06793 break;
06794 case 'n':
06795 pridialplan = PRI_NPI_NATIONAL | (pridialplan & 0xf0);
06796 break;
06797 case 'p':
06798 pridialplan = PRI_NPI_PRIVATE | (pridialplan & 0xf0);
06799 break;
06800 case 'r':
06801 pridialplan = PRI_NPI_RESERVED | (pridialplan & 0xf0);
06802 break;
06803 default:
06804 if (isalpha(c[p->stripmsd])) {
06805 ast_log(LOG_WARNING, "Unrecognized pridialplan %s modifier: %c\n",
06806 c[p->stripmsd] > 'Z' ? "NPI" : "TON", c[p->stripmsd]);
06807 }
06808 break;
06809 }
06810 c++;
06811 }
06812 #if defined(HAVE_PRI_SETUP_KEYPAD)
06813 if (ast_test_flag(&opts, OPT_KEYPAD)
06814 && !ast_strlen_zero(opt_args[OPT_ARG_KEYPAD])) {
06815
06816 keypad = opt_args[OPT_ARG_KEYPAD];
06817 pri_sr_set_keypad_digits(sr, keypad);
06818 } else {
06819 keypad = NULL;
06820 }
06821 if (!keypad || !ast_strlen_zero(c + p->stripmsd + dp_strip))
06822 #endif
06823 {
06824 pri_sr_set_called(sr, c + p->stripmsd + dp_strip, pridialplan, s ? 1 : 0);
06825 }
06826
06827 #if defined(HAVE_PRI_SUBADDR)
06828 if (dialed_subaddress.valid) {
06829 struct pri_party_subaddress subaddress;
06830
06831 memset(&subaddress, 0, sizeof(subaddress));
06832 sig_pri_party_subaddress_from_ast(&subaddress, &dialed_subaddress);
06833 pri_sr_set_called_subaddress(sr, &subaddress);
06834 }
06835 #endif
06836 #if defined(HAVE_PRI_REVERSE_CHARGE)
06837 if (ast_test_flag(&opts, OPT_REVERSE_CHARGE)) {
06838 pri_sr_set_reversecharge(sr, PRI_REVERSECHARGE_REQUESTED);
06839 }
06840 #endif
06841 #if defined(HAVE_PRI_AOC_EVENTS)
06842 if (ast_test_flag(&opts, OPT_AOC_REQUEST)
06843 && !ast_strlen_zero(opt_args[OPT_ARG_AOC_REQUEST])) {
06844 if (strchr(opt_args[OPT_ARG_AOC_REQUEST], 's')) {
06845 pri_sr_set_aoc_charging_request(sr, PRI_AOC_REQUEST_S);
06846 }
06847 if (strchr(opt_args[OPT_ARG_AOC_REQUEST], 'd')) {
06848 pri_sr_set_aoc_charging_request(sr, PRI_AOC_REQUEST_D);
06849 }
06850 if (strchr(opt_args[OPT_ARG_AOC_REQUEST], 'e')) {
06851 pri_sr_set_aoc_charging_request(sr, PRI_AOC_REQUEST_E);
06852 }
06853 }
06854 #endif
06855
06856
06857 if (p->pri->append_msn_to_user_tag) {
06858 snprintf(p->user_tag, sizeof(p->user_tag), "%s_%s", p->pri->initial_user_tag,
06859 p->pri->nodetype == PRI_NETWORK
06860 ? c + p->stripmsd + dp_strip
06861 : S_COR(ast->connected.id.number.valid,
06862 ast->connected.id.number.str, ""));
06863 } else {
06864 ast_copy_string(p->user_tag, p->pri->initial_user_tag, sizeof(p->user_tag));
06865 }
06866
06867
06868
06869
06870
06871 ast_free(ast->caller.id.tag);
06872 ast->caller.id.tag = ast_strdup(p->user_tag);
06873
06874 ldp_strip = 0;
06875 prilocaldialplan = p->pri->localdialplan - 1;
06876 if ((l != NULL) && (prilocaldialplan == -2 || prilocaldialplan == -3)) {
06877 if (strncmp(l, p->pri->internationalprefix, strlen(p->pri->internationalprefix)) == 0) {
06878 if (prilocaldialplan == -2) {
06879 ldp_strip = strlen(p->pri->internationalprefix);
06880 }
06881 prilocaldialplan = PRI_INTERNATIONAL_ISDN;
06882 } else if (strncmp(l, p->pri->nationalprefix, strlen(p->pri->nationalprefix)) == 0) {
06883 if (prilocaldialplan == -2) {
06884 ldp_strip = strlen(p->pri->nationalprefix);
06885 }
06886 prilocaldialplan = PRI_NATIONAL_ISDN;
06887 } else {
06888 prilocaldialplan = PRI_LOCAL_ISDN;
06889 }
06890 }
06891 if (l != NULL) {
06892 while (*l > '9' && *l != '*' && *l != '#') {
06893 switch (*l) {
06894 case 'U':
06895 prilocaldialplan = (PRI_TON_UNKNOWN << 4) | (prilocaldialplan & 0xf);
06896 break;
06897 case 'I':
06898 prilocaldialplan = (PRI_TON_INTERNATIONAL << 4) | (prilocaldialplan & 0xf);
06899 break;
06900 case 'N':
06901 prilocaldialplan = (PRI_TON_NATIONAL << 4) | (prilocaldialplan & 0xf);
06902 break;
06903 case 'L':
06904 prilocaldialplan = (PRI_TON_NET_SPECIFIC << 4) | (prilocaldialplan & 0xf);
06905 break;
06906 case 'S':
06907 prilocaldialplan = (PRI_TON_SUBSCRIBER << 4) | (prilocaldialplan & 0xf);
06908 break;
06909 case 'V':
06910 prilocaldialplan = (PRI_TON_ABBREVIATED << 4) | (prilocaldialplan & 0xf);
06911 break;
06912 case 'R':
06913 prilocaldialplan = (PRI_TON_RESERVED << 4) | (prilocaldialplan & 0xf);
06914 break;
06915 case 'u':
06916 prilocaldialplan = PRI_NPI_UNKNOWN | (prilocaldialplan & 0xf0);
06917 break;
06918 case 'e':
06919 prilocaldialplan = PRI_NPI_E163_E164 | (prilocaldialplan & 0xf0);
06920 break;
06921 case 'x':
06922 prilocaldialplan = PRI_NPI_X121 | (prilocaldialplan & 0xf0);
06923 break;
06924 case 'f':
06925 prilocaldialplan = PRI_NPI_F69 | (prilocaldialplan & 0xf0);
06926 break;
06927 case 'n':
06928 prilocaldialplan = PRI_NPI_NATIONAL | (prilocaldialplan & 0xf0);
06929 break;
06930 case 'p':
06931 prilocaldialplan = PRI_NPI_PRIVATE | (prilocaldialplan & 0xf0);
06932 break;
06933 case 'r':
06934 prilocaldialplan = PRI_NPI_RESERVED | (prilocaldialplan & 0xf0);
06935 break;
06936 default:
06937 if (isalpha(*l)) {
06938 ast_log(LOG_WARNING,
06939 "Unrecognized prilocaldialplan %s modifier: %c\n",
06940 *l > 'Z' ? "NPI" : "TON", *l);
06941 }
06942 break;
06943 }
06944 l++;
06945 }
06946 }
06947 pri_sr_set_caller(sr, l ? (l + ldp_strip) : NULL, n, prilocaldialplan,
06948 p->use_callingpres ? ast->connected.id.number.presentation : (l ? PRES_ALLOWED_USER_NUMBER_PASSED_SCREEN : PRES_NUMBER_NOT_AVAILABLE));
06949
06950 #if defined(HAVE_PRI_SUBADDR)
06951 if (ast->connected.id.subaddress.valid) {
06952 struct pri_party_subaddress subaddress;
06953
06954 memset(&subaddress, 0, sizeof(subaddress));
06955 sig_pri_party_subaddress_from_ast(&subaddress, &ast->connected.id.subaddress);
06956 pri_sr_set_caller_subaddress(sr, &subaddress);
06957 }
06958 #endif
06959
06960 sig_pri_redirecting_update(p, ast);
06961
06962 #ifdef SUPPORT_USERUSER
06963
06964 useruser = pbx_builtin_getvar_helper(p->owner, "USERUSERINFO");
06965 if (useruser)
06966 pri_sr_set_useruser(sr, useruser);
06967 #endif
06968
06969 #if defined(HAVE_PRI_CCSS)
06970 if (ast_cc_is_recall(ast, &core_id, sig_pri_cc_type_name)) {
06971 struct ast_cc_monitor *monitor;
06972 char device_name[AST_CHANNEL_NAME];
06973
06974
06975 ast_channel_get_device_name(ast, device_name, sizeof(device_name));
06976 monitor = ast_cc_get_monitor_by_recall_core_id(core_id, device_name);
06977 if (monitor) {
06978 struct sig_pri_cc_monitor_instance *instance;
06979
06980 instance = monitor->private_data;
06981
06982
06983 ast_assert(p->pri == instance->pri);
06984
06985 if (pri_cc_call(p->pri->pri, instance->cc_id, p->call, sr)) {
06986
06987 ast_log(LOG_WARNING, "Unable to setup CC recall call to device %s\n",
06988 device_name);
06989 ao2_ref(monitor, -1);
06990 pri_destroycall(p->pri->pri, p->call);
06991 p->call = NULL;
06992 pri_rel(p->pri);
06993 pri_sr_free(sr);
06994 return -1;
06995 }
06996 ao2_ref(monitor, -1);
06997 } else {
06998 core_id = -1;
06999 }
07000 } else
07001 #endif
07002 {
07003 core_id = -1;
07004 }
07005 if (core_id == -1 && pri_setup(p->pri->pri, p->call, sr)) {
07006 ast_log(LOG_WARNING, "Unable to setup call to %s (using %s)\n",
07007 c + p->stripmsd + dp_strip, dialplan2str(p->pri->dialplan));
07008 pri_destroycall(p->pri->pri, p->call);
07009 p->call = NULL;
07010 pri_rel(p->pri);
07011 pri_sr_free(sr);
07012 return -1;
07013 }
07014 p->call_level = SIG_PRI_CALL_LEVEL_SETUP;
07015 pri_sr_free(sr);
07016 ast_setstate(ast, AST_STATE_DIALING);
07017 sig_pri_set_dialing(p, 1);
07018 pri_rel(p->pri);
07019 return 0;
07020 }
07021
07022 int sig_pri_indicate(struct sig_pri_chan *p, struct ast_channel *chan, int condition, const void *data, size_t datalen)
07023 {
07024 int res = -1;
07025
07026 switch (condition) {
07027 case AST_CONTROL_BUSY:
07028 if (p->priindication_oob || p->no_b_channel) {
07029 chan->hangupcause = AST_CAUSE_USER_BUSY;
07030 chan->_softhangup |= AST_SOFTHANGUP_DEV;
07031 res = 0;
07032 break;
07033 }
07034 res = sig_pri_play_tone(p, SIG_PRI_TONE_BUSY);
07035 if (p->call_level < SIG_PRI_CALL_LEVEL_ALERTING && !p->outgoing) {
07036 chan->hangupcause = AST_CAUSE_USER_BUSY;
07037 p->progress = 1;
07038 if (p->pri && p->pri->pri) {
07039 pri_grab(p, p->pri);
07040 #ifdef HAVE_PRI_PROG_W_CAUSE
07041 pri_progress_with_cause(p->pri->pri, p->call, PVT_TO_CHANNEL(p), 1, chan->hangupcause);
07042 #else
07043 pri_progress(p->pri->pri,p->call, PVT_TO_CHANNEL(p), 1);
07044 #endif
07045 pri_rel(p->pri);
07046 }
07047 }
07048 break;
07049 case AST_CONTROL_RINGING:
07050 if (p->call_level < SIG_PRI_CALL_LEVEL_ALERTING && !p->outgoing) {
07051 p->call_level = SIG_PRI_CALL_LEVEL_ALERTING;
07052 if (p->pri && p->pri->pri) {
07053 pri_grab(p, p->pri);
07054 pri_acknowledge(p->pri->pri,p->call, PVT_TO_CHANNEL(p),
07055 p->no_b_channel || p->digital ? 0 : 1);
07056 pri_rel(p->pri);
07057 }
07058 }
07059 res = sig_pri_play_tone(p, SIG_PRI_TONE_RINGTONE);
07060 if (chan->_state != AST_STATE_UP) {
07061 if (chan->_state != AST_STATE_RING)
07062 ast_setstate(chan, AST_STATE_RINGING);
07063 }
07064 break;
07065 case AST_CONTROL_PROCEEDING:
07066 ast_debug(1,"Received AST_CONTROL_PROCEEDING on %s\n",chan->name);
07067 if (p->call_level < SIG_PRI_CALL_LEVEL_PROCEEDING && !p->outgoing) {
07068 p->call_level = SIG_PRI_CALL_LEVEL_PROCEEDING;
07069 if (p->pri && p->pri->pri) {
07070 pri_grab(p, p->pri);
07071 pri_proceeding(p->pri->pri,p->call, PVT_TO_CHANNEL(p),
07072 p->no_b_channel || p->digital ? 0 : 1);
07073 if (!p->no_b_channel && !p->digital) {
07074 sig_pri_set_dialing(p, 0);
07075 }
07076 pri_rel(p->pri);
07077 }
07078 }
07079
07080 res = 0;
07081 break;
07082 case AST_CONTROL_PROGRESS:
07083 ast_debug(1,"Received AST_CONTROL_PROGRESS on %s\n",chan->name);
07084 sig_pri_set_digital(p, 0);
07085 if (!p->progress && p->call_level < SIG_PRI_CALL_LEVEL_ALERTING && !p->outgoing
07086 && !p->no_b_channel) {
07087 p->progress = 1;
07088 if (p->pri && p->pri->pri) {
07089 pri_grab(p, p->pri);
07090 #ifdef HAVE_PRI_PROG_W_CAUSE
07091 pri_progress_with_cause(p->pri->pri,p->call, PVT_TO_CHANNEL(p), 1, -1);
07092 #else
07093 pri_progress(p->pri->pri,p->call, PVT_TO_CHANNEL(p), 1);
07094 #endif
07095 pri_rel(p->pri);
07096 }
07097 }
07098
07099 res = 0;
07100 break;
07101 case AST_CONTROL_INCOMPLETE:
07102
07103 if (p->call_level == SIG_PRI_CALL_LEVEL_CONNECT || (p->pri->overlapdial & DAHDI_OVERLAPDIAL_INCOMING)) {
07104 res = 0;
07105 break;
07106 }
07107
07108 chan->hangupcause = AST_CAUSE_INVALID_NUMBER_FORMAT;
07109
07110 case AST_CONTROL_CONGESTION:
07111 if (p->priindication_oob || p->no_b_channel) {
07112
07113 switch (chan->hangupcause) {
07114 case AST_CAUSE_USER_BUSY:
07115 case AST_CAUSE_NORMAL_CLEARING:
07116 case 0:
07117
07118 chan->hangupcause = AST_CAUSE_SWITCH_CONGESTION;
07119 break;
07120 default:
07121 break;
07122 }
07123 chan->_softhangup |= AST_SOFTHANGUP_DEV;
07124 res = 0;
07125 break;
07126 }
07127 res = sig_pri_play_tone(p, SIG_PRI_TONE_CONGESTION);
07128 if (p->call_level < SIG_PRI_CALL_LEVEL_ALERTING && !p->outgoing) {
07129
07130 switch (chan->hangupcause) {
07131 case AST_CAUSE_USER_BUSY:
07132 case AST_CAUSE_NORMAL_CLEARING:
07133 case 0:
07134
07135 chan->hangupcause = AST_CAUSE_SWITCH_CONGESTION;
07136 break;
07137 default:
07138 break;
07139 }
07140 p->progress = 1;
07141 if (p->pri && p->pri->pri) {
07142 pri_grab(p, p->pri);
07143 #ifdef HAVE_PRI_PROG_W_CAUSE
07144 pri_progress_with_cause(p->pri->pri, p->call, PVT_TO_CHANNEL(p), 1, chan->hangupcause);
07145 #else
07146 pri_progress(p->pri->pri,p->call, PVT_TO_CHANNEL(p), 1);
07147 #endif
07148 pri_rel(p->pri);
07149 }
07150 }
07151 break;
07152 case AST_CONTROL_HOLD:
07153 if (p->pri && !strcasecmp(p->mohinterpret, "passthrough")) {
07154 pri_grab(p, p->pri);
07155 res = pri_notify(p->pri->pri, p->call, p->prioffset, PRI_NOTIFY_REMOTE_HOLD);
07156 pri_rel(p->pri);
07157 } else
07158 ast_moh_start(chan, data, p->mohinterpret);
07159 break;
07160 case AST_CONTROL_UNHOLD:
07161 if (p->pri && !strcasecmp(p->mohinterpret, "passthrough")) {
07162 pri_grab(p, p->pri);
07163 res = pri_notify(p->pri->pri, p->call, p->prioffset, PRI_NOTIFY_REMOTE_RETRIEVAL);
07164 pri_rel(p->pri);
07165 } else
07166 ast_moh_stop(chan);
07167 break;
07168 case AST_CONTROL_SRCUPDATE:
07169 res = 0;
07170 break;
07171 case -1:
07172 res = sig_pri_play_tone(p, -1);
07173 break;
07174 case AST_CONTROL_CONNECTED_LINE:
07175 ast_debug(1, "Received AST_CONTROL_CONNECTED_LINE on %s\n", chan->name);
07176 if (p->pri) {
07177 struct pri_party_connected_line connected;
07178
07179 pri_grab(p, p->pri);
07180 memset(&connected, 0, sizeof(connected));
07181 sig_pri_party_id_from_ast(&connected.id, &chan->connected.id);
07182
07183 pri_connected_line_update(p->pri->pri, p->call, &connected);
07184 pri_rel(p->pri);
07185 }
07186 break;
07187 case AST_CONTROL_REDIRECTING:
07188 ast_debug(1, "Received AST_CONTROL_REDIRECTING on %s\n", chan->name);
07189 if (p->pri) {
07190 pri_grab(p, p->pri);
07191 sig_pri_redirecting_update(p, chan);
07192 pri_rel(p->pri);
07193 }
07194 break;
07195 case AST_CONTROL_AOC:
07196 #if defined(HAVE_PRI_AOC_EVENTS)
07197 {
07198 struct ast_aoc_decoded *decoded
07199 = ast_aoc_decode((struct ast_aoc_encoded *) data, datalen, chan);
07200 ast_debug(1, "Received AST_CONTROL_AOC on %s\n", chan->name);
07201 if (decoded && p->pri) {
07202 pri_grab(p, p->pri);
07203 switch (ast_aoc_get_msg_type(decoded)) {
07204 case AST_AOC_S:
07205 if (p->pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_S) {
07206 sig_pri_aoc_s_from_ast(p, decoded);
07207 }
07208 break;
07209 case AST_AOC_D:
07210 if (p->pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_D) {
07211 sig_pri_aoc_d_from_ast(p, decoded);
07212 }
07213 break;
07214 case AST_AOC_E:
07215 if (p->pri->aoc_passthrough_flag & SIG_PRI_AOC_GRANT_E) {
07216 sig_pri_aoc_e_from_ast(p, decoded);
07217 }
07218
07219
07220
07221
07222 if (p->waiting_for_aoce) {
07223 p->waiting_for_aoce = 0;
07224 ast_log(LOG_DEBUG,
07225 "Received final AOC-E msg, continue with hangup on %s\n",
07226 chan->name);
07227 ast_softhangup_nolock(chan, AST_SOFTHANGUP_DEV);
07228 }
07229 break;
07230 case AST_AOC_REQUEST:
07231
07232
07233 if (ast_aoc_get_termination_request(decoded)) {
07234 pri_hangup(p->pri->pri, p->call, -1);
07235 }
07236 break;
07237 default:
07238 break;
07239 }
07240 pri_rel(p->pri);
07241 }
07242 ast_aoc_destroy_decoded(decoded);
07243 }
07244 #endif
07245 break;
07246 }
07247
07248 return res;
07249 }
07250
07251 int sig_pri_answer(struct sig_pri_chan *p, struct ast_channel *ast)
07252 {
07253 int res;
07254
07255
07256 pri_grab(p, p->pri);
07257 #if defined(HAVE_PRI_AOC_EVENTS)
07258 if (p->aoc_s_request_invoke_id_valid) {
07259
07260
07261
07262 pri_aoc_s_request_response_send(p->pri->pri, p->call,
07263 p->aoc_s_request_invoke_id, NULL);
07264 p->aoc_s_request_invoke_id_valid = 0;
07265 }
07266 #endif
07267 if (p->call_level < SIG_PRI_CALL_LEVEL_CONNECT) {
07268 p->call_level = SIG_PRI_CALL_LEVEL_CONNECT;
07269 }
07270 sig_pri_set_dialing(p, 0);
07271 sig_pri_open_media(p);
07272 res = pri_answer(p->pri->pri, p->call, 0, !p->digital);
07273 pri_rel(p->pri);
07274 ast_setstate(ast, AST_STATE_UP);
07275 return res;
07276 }
07277
07278
07279
07280
07281
07282
07283
07284
07285
07286
07287
07288 static int sig_pri_available_check(struct sig_pri_chan *pvt)
07289 {
07290
07291
07292
07293
07294 if (!pvt->no_b_channel && sig_pri_is_chan_available(pvt)) {
07295 return 1;
07296 }
07297 return 0;
07298 }
07299
07300 #if defined(HAVE_PRI_CALL_WAITING)
07301
07302
07303
07304
07305
07306
07307
07308
07309
07310
07311
07312
07313 static struct sig_pri_chan *sig_pri_cw_available(struct sig_pri_span *pri)
07314 {
07315 struct sig_pri_chan *cw;
07316 int idx;
07317
07318 cw = NULL;
07319 if (pri->num_call_waiting_calls < pri->max_call_waiting_calls) {
07320 if (!pri->num_call_waiting_calls) {
07321
07322
07323
07324
07325
07326 for (idx = 0; idx < pri->numchans; ++idx) {
07327 if (pri->pvts[idx] && sig_pri_available_check(pri->pvts[idx])) {
07328
07329 return cw;
07330 }
07331 }
07332 }
07333 idx = pri_find_empty_nobch(pri);
07334 if (0 <= idx) {
07335
07336 cw = pri->pvts[idx];
07337 cw->is_call_waiting = 1;
07338 sig_pri_init_config(cw, pri);
07339 ast_atomic_fetchadd_int(&pri->num_call_waiting_calls, 1);
07340 }
07341 }
07342 return cw;
07343 }
07344 #endif
07345
07346 int sig_pri_available(struct sig_pri_chan **pvt, int is_specific_channel)
07347 {
07348 struct sig_pri_chan *p = *pvt;
07349 struct sig_pri_span *pri;
07350
07351 if (!p->pri) {
07352
07353 return 0;
07354 }
07355 pri = p->pri;
07356
07357 ast_mutex_lock(&pri->lock);
07358 if (
07359 #if defined(HAVE_PRI_CALL_WAITING)
07360
07361
07362
07363
07364
07365
07366 !pri->num_call_waiting_calls &&
07367 #endif
07368 sig_pri_available_check(p)) {
07369 p->allocated = 1;
07370 ast_mutex_unlock(&pri->lock);
07371 return 1;
07372 }
07373
07374 #if defined(HAVE_PRI_CALL_WAITING)
07375 if (!is_specific_channel) {
07376 struct sig_pri_chan *cw;
07377
07378 cw = sig_pri_cw_available(pri);
07379 if (cw) {
07380
07381 cw->allocated = 1;
07382 *pvt = cw;
07383 ast_mutex_unlock(&pri->lock);
07384 return 1;
07385 }
07386 }
07387 #endif
07388 ast_mutex_unlock(&pri->lock);
07389 return 0;
07390 }
07391
07392
07393
07394 int sig_pri_digit_begin(struct sig_pri_chan *pvt, struct ast_channel *ast, char digit)
07395 {
07396 if (ast->_state == AST_STATE_DIALING) {
07397 if (pvt->call_level < SIG_PRI_CALL_LEVEL_OVERLAP) {
07398 unsigned int len;
07399
07400 len = strlen(pvt->dialdest);
07401 if (len < sizeof(pvt->dialdest) - 1) {
07402 ast_debug(1, "Queueing digit '%c' since setup_ack not yet received\n",
07403 digit);
07404 pvt->dialdest[len++] = digit;
07405 pvt->dialdest[len] = '\0';
07406 } else {
07407 ast_log(LOG_WARNING,
07408 "Span %d: Deferred digit buffer overflow for digit '%c'.\n",
07409 pvt->pri->span, digit);
07410 }
07411 return 0;
07412 }
07413 if (pvt->call_level < SIG_PRI_CALL_LEVEL_PROCEEDING) {
07414 pri_grab(pvt, pvt->pri);
07415 pri_information(pvt->pri->pri, pvt->call, digit);
07416 pri_rel(pvt->pri);
07417 return 0;
07418 }
07419 if (pvt->call_level < SIG_PRI_CALL_LEVEL_CONNECT) {
07420 ast_log(LOG_WARNING,
07421 "Span %d: Digit '%c' may be ignored by peer. (Call level:%d(%s))\n",
07422 pvt->pri->span, digit, pvt->call_level,
07423 sig_pri_call_level2str(pvt->call_level));
07424 }
07425 }
07426 return 1;
07427 }
07428
07429
07430
07431
07432
07433
07434
07435
07436
07437
07438
07439
07440 void sig_pri_dial_complete(struct sig_pri_chan *pvt, struct ast_channel *ast)
07441 {
07442
07443 if (pvt->call_level == SIG_PRI_CALL_LEVEL_DEFER_DIAL) {
07444 pvt->call_level = SIG_PRI_CALL_LEVEL_CONNECT;
07445
07446 sig_pri_open_media(pvt);
07447 {
07448 struct ast_frame f = {AST_FRAME_CONTROL, };
07449
07450 if (pvt->calls->queue_control) {
07451 pvt->calls->queue_control(pvt->chan_pvt, AST_CONTROL_ANSWER);
07452 }
07453
07454 f.subclass.integer = AST_CONTROL_ANSWER;
07455 ast_queue_frame(ast, &f);
07456 }
07457 sig_pri_set_dialing(pvt, 0);
07458
07459 sig_pri_set_echocanceller(pvt, 1);
07460 }
07461 }
07462
07463 #if defined(HAVE_PRI_MWI)
07464
07465
07466
07467
07468
07469
07470
07471
07472
07473
07474
07475
07476 static void sig_pri_send_mwi_indication(struct sig_pri_span *pri, const char *mbox_number, const char *mbox_context, int num_messages)
07477 {
07478 struct pri_party_id mailbox;
07479
07480 ast_debug(1, "Send MWI indication for %s@%s num_messages:%d\n", mbox_number,
07481 mbox_context, num_messages);
07482
07483 memset(&mailbox, 0, sizeof(mailbox));
07484 mailbox.number.valid = 1;
07485 mailbox.number.presentation = PRES_ALLOWED_USER_NUMBER_NOT_SCREENED;
07486 mailbox.number.plan = (PRI_TON_UNKNOWN << 4) | PRI_NPI_UNKNOWN;
07487 ast_copy_string(mailbox.number.str, mbox_number, sizeof(mailbox.number.str));
07488
07489 ast_mutex_lock(&pri->lock);
07490 pri_mwi_indicate(pri->pri, &mailbox, 1 , num_messages, NULL, NULL, -1, 0);
07491 ast_mutex_unlock(&pri->lock);
07492 }
07493 #endif
07494
07495 #if defined(HAVE_PRI_MWI)
07496
07497
07498
07499
07500
07501
07502
07503
07504
07505
07506 static void sig_pri_mwi_event_cb(const struct ast_event *event, void *userdata)
07507 {
07508 struct sig_pri_span *pri = userdata;
07509 const char *mbox_context;
07510 const char *mbox_number;
07511 int num_messages;
07512
07513 mbox_number = ast_event_get_ie_str(event, AST_EVENT_IE_MAILBOX);
07514 if (ast_strlen_zero(mbox_number)) {
07515 return;
07516 }
07517 mbox_context = ast_event_get_ie_str(event, AST_EVENT_IE_CONTEXT);
07518 if (ast_strlen_zero(mbox_context)) {
07519 return;
07520 }
07521 num_messages = ast_event_get_ie_uint(event, AST_EVENT_IE_NEWMSGS);
07522 sig_pri_send_mwi_indication(pri, mbox_number, mbox_context, num_messages);
07523 }
07524 #endif
07525
07526 #if defined(HAVE_PRI_MWI)
07527
07528
07529
07530
07531
07532
07533
07534
07535
07536 static void sig_pri_mwi_cache_update(struct sig_pri_span *pri)
07537 {
07538 int idx;
07539 int num_messages;
07540 struct ast_event *event;
07541
07542 for (idx = 0; idx < ARRAY_LEN(pri->mbox); ++idx) {
07543 if (!pri->mbox[idx].sub) {
07544
07545 break;
07546 }
07547
07548 event = ast_event_get_cached(AST_EVENT_MWI,
07549 AST_EVENT_IE_MAILBOX, AST_EVENT_IE_PLTYPE_STR, pri->mbox[idx].number,
07550 AST_EVENT_IE_CONTEXT, AST_EVENT_IE_PLTYPE_STR, pri->mbox[idx].context,
07551 AST_EVENT_IE_END);
07552 if (!event) {
07553
07554 continue;
07555 }
07556 num_messages = ast_event_get_ie_uint(event, AST_EVENT_IE_NEWMSGS);
07557 sig_pri_send_mwi_indication(pri, pri->mbox[idx].number, pri->mbox[idx].context,
07558 num_messages);
07559 ast_event_destroy(event);
07560 }
07561 }
07562 #endif
07563
07564
07565
07566
07567
07568
07569
07570
07571
07572 void sig_pri_stop_pri(struct sig_pri_span *pri)
07573 {
07574 #if defined(HAVE_PRI_MWI)
07575 int idx;
07576 #endif
07577
07578 #if defined(HAVE_PRI_MWI)
07579 for (idx = 0; idx < ARRAY_LEN(pri->mbox); ++idx) {
07580 if (pri->mbox[idx].sub) {
07581 pri->mbox[idx].sub = ast_event_unsubscribe(pri->mbox[idx].sub);
07582 }
07583 }
07584 #endif
07585 }
07586
07587
07588
07589
07590
07591
07592
07593
07594
07595
07596
07597
07598
07599 static int sig_pri_cmp_pri_chans(const void *left, const void *right)
07600 {
07601 const struct sig_pri_chan *pvt_left;
07602 const struct sig_pri_chan *pvt_right;
07603
07604 pvt_left = *(struct sig_pri_chan **) left;
07605 pvt_right = *(struct sig_pri_chan **) right;
07606 if (!pvt_left) {
07607 if (!pvt_right) {
07608 return 0;
07609 }
07610 return 1;
07611 }
07612 if (!pvt_right) {
07613 return -1;
07614 }
07615
07616 return pvt_left->channel - pvt_right->channel;
07617 }
07618
07619
07620
07621
07622
07623
07624
07625
07626
07627
07628
07629
07630
07631
07632 static void sig_pri_sort_pri_chans(struct sig_pri_span *pri)
07633 {
07634 qsort(&pri->pvts, pri->numchans, sizeof(pri->pvts[0]), sig_pri_cmp_pri_chans);
07635 }
07636
07637 int sig_pri_start_pri(struct sig_pri_span *pri)
07638 {
07639 int x;
07640 int i;
07641 #if defined(HAVE_PRI_MWI)
07642 char *saveptr;
07643 char *mbox_number;
07644 char *mbox_context;
07645 struct ast_str *mwi_description = ast_str_alloca(64);
07646 #endif
07647
07648 #if defined(HAVE_PRI_MWI)
07649
07650 for (i = 0; i < ARRAY_LEN(pri->mbox); ++i) {
07651 if (pri->mbox[i].sub) {
07652 pri->mbox[i].sub = ast_event_unsubscribe(pri->mbox[i].sub);
07653 }
07654 }
07655 #endif
07656
07657 ast_mutex_init(&pri->lock);
07658 sig_pri_sort_pri_chans(pri);
07659
07660 #if defined(HAVE_PRI_MWI)
07661
07662
07663
07664
07665 i = 0;
07666 saveptr = pri->mwi_mailboxes;
07667 while (i < ARRAY_LEN(pri->mbox)) {
07668 mbox_number = strsep(&saveptr, ",");
07669 if (!mbox_number) {
07670 break;
07671 }
07672
07673 mbox_context = strchr(mbox_number, '@');
07674 if (mbox_context) {
07675 *mbox_context++ = '\0';
07676 mbox_context = ast_strip(mbox_context);
07677 }
07678 mbox_number = ast_strip(mbox_number);
07679 if (ast_strlen_zero(mbox_number)) {
07680
07681 continue;
07682 }
07683 if (ast_strlen_zero(mbox_context)) {
07684
07685 mbox_context = "default";
07686 }
07687
07688
07689 ast_str_set(&mwi_description, -1, "%s span %d[%d] MWI mailbox %s@%s",
07690 sig_pri_cc_type_name, pri->span, i, mbox_number, mbox_context);
07691 pri->mbox[i].sub = ast_event_subscribe(AST_EVENT_MWI, sig_pri_mwi_event_cb,
07692 ast_str_buffer(mwi_description), pri,
07693 AST_EVENT_IE_MAILBOX, AST_EVENT_IE_PLTYPE_STR, mbox_number,
07694 AST_EVENT_IE_CONTEXT, AST_EVENT_IE_PLTYPE_STR, mbox_context,
07695 AST_EVENT_IE_END);
07696 if (!pri->mbox[i].sub) {
07697 ast_log(LOG_ERROR, "%s span %d could not subscribe to MWI events for %s@%s.",
07698 sig_pri_cc_type_name, pri->span, mbox_number, mbox_context);
07699 continue;
07700 }
07701 pri->mbox[i].number = mbox_number;
07702 pri->mbox[i].context = mbox_context;
07703 ++i;
07704 }
07705 #endif
07706
07707 for (i = 0; i < SIG_PRI_NUM_DCHANS; i++) {
07708 if (pri->fds[i] == -1) {
07709 break;
07710 }
07711
07712 switch (pri->sig) {
07713 case SIG_BRI:
07714 pri->dchans[i] = pri_new_bri(pri->fds[i], 1, pri->nodetype, pri->switchtype);
07715 break;
07716 case SIG_BRI_PTMP:
07717 pri->dchans[i] = pri_new_bri(pri->fds[i], 0, pri->nodetype, pri->switchtype);
07718 break;
07719 default:
07720 pri->dchans[i] = pri_new(pri->fds[i], pri->nodetype, pri->switchtype);
07721 #if defined(HAVE_PRI_SERVICE_MESSAGES)
07722 if (pri->enable_service_message_support) {
07723 pri_set_service_message_support(pri->dchans[i], 1);
07724 }
07725 #endif
07726 break;
07727 }
07728
07729 pri_set_overlapdial(pri->dchans[i], (pri->overlapdial & DAHDI_OVERLAPDIAL_OUTGOING) ? 1 : 0);
07730 #ifdef HAVE_PRI_PROG_W_CAUSE
07731 pri_set_chan_mapping_logical(pri->dchans[i], pri->qsigchannelmapping == DAHDI_CHAN_MAPPING_LOGICAL);
07732 #endif
07733 #ifdef HAVE_PRI_INBANDDISCONNECT
07734 pri_set_inbanddisconnect(pri->dchans[i], pri->inbanddisconnect);
07735 #endif
07736
07737 if (i)
07738 pri_enslave(pri->dchans[0], pri->dchans[i]);
07739 if (!pri->dchans[i]) {
07740 if (pri->fds[i] > 0)
07741 close(pri->fds[i]);
07742 pri->fds[i] = -1;
07743 ast_log(LOG_ERROR, "Unable to create PRI structure\n");
07744 return -1;
07745 }
07746 pri_set_debug(pri->dchans[i], SIG_PRI_DEBUG_DEFAULT);
07747 pri_set_nsf(pri->dchans[i], pri->nsf);
07748 #ifdef PRI_GETSET_TIMERS
07749 for (x = 0; x < PRI_MAX_TIMERS; x++) {
07750 if (pri->pritimers[x] != 0)
07751 pri_set_timer(pri->dchans[i], x, pri->pritimers[x]);
07752 }
07753 #endif
07754 }
07755
07756
07757 pri->pri = pri->dchans[0];
07758
07759 #if defined(HAVE_PRI_CALL_HOLD)
07760 pri_hold_enable(pri->pri, 1);
07761 #endif
07762 #if defined(HAVE_PRI_CALL_REROUTING)
07763 pri_reroute_enable(pri->pri, 1);
07764 #endif
07765 #if defined(HAVE_PRI_HANGUP_FIX)
07766 pri_hangup_fix_enable(pri->pri, 1);
07767 #endif
07768 #if defined(HAVE_PRI_CCSS)
07769 pri_cc_enable(pri->pri, 1);
07770 pri_cc_recall_mode(pri->pri, pri->cc_ptmp_recall_mode);
07771 pri_cc_retain_signaling_req(pri->pri, pri->cc_qsig_signaling_link_req);
07772 pri_cc_retain_signaling_rsp(pri->pri, pri->cc_qsig_signaling_link_rsp);
07773 #endif
07774 #if defined(HAVE_PRI_TRANSFER)
07775 pri_transfer_enable(pri->pri, 1);
07776 #endif
07777 #if defined(HAVE_PRI_AOC_EVENTS)
07778 pri_aoc_events_enable(pri->pri, 1);
07779 #endif
07780 #if defined(HAVE_PRI_CALL_WAITING)
07781 pri_connect_ack_enable(pri->pri, 1);
07782 #endif
07783 #if defined(HAVE_PRI_MCID)
07784 pri_mcid_enable(pri->pri, 1);
07785 #endif
07786 #if defined(HAVE_PRI_L2_PERSISTENCE)
07787 pri_persistent_layer2_option(pri->pri, pri->l2_persistence);
07788 #endif
07789
07790 pri->resetpos = -1;
07791 if (ast_pthread_create_background(&pri->master, NULL, pri_dchannel, pri)) {
07792 for (i = 0; i < SIG_PRI_NUM_DCHANS; i++) {
07793 if (!pri->dchans[i])
07794 break;
07795 if (pri->fds[i] > 0)
07796 close(pri->fds[i]);
07797 pri->fds[i] = -1;
07798 }
07799 ast_log(LOG_ERROR, "Unable to spawn D-channel: %s\n", strerror(errno));
07800 return -1;
07801 }
07802
07803 #if defined(HAVE_PRI_MWI)
07804
07805
07806
07807
07808
07809
07810
07811
07812 sig_pri_mwi_cache_update(pri);
07813 #endif
07814
07815 return 0;
07816 }
07817
07818
07819
07820
07821
07822
07823
07824
07825
07826
07827
07828 void sig_pri_chan_alarm_notify(struct sig_pri_chan *p, int noalarm)
07829 {
07830 pri_grab(p, p->pri);
07831 sig_pri_set_alarm(p, !noalarm);
07832 if (!noalarm) {
07833 if (pri_get_timer(p->pri->pri, PRI_TIMER_T309) < 0) {
07834
07835 if (p->call) {
07836 pri_destroycall(p->pri->pri, p->call);
07837 p->call = NULL;
07838 }
07839 if (p->owner)
07840 p->owner->_softhangup |= AST_SOFTHANGUP_DEV;
07841 }
07842 }
07843 sig_pri_span_devstate_changed(p->pri);
07844 pri_rel(p->pri);
07845 }
07846
07847
07848
07849
07850
07851
07852
07853
07854 int sig_pri_is_alarm_ignored(struct sig_pri_span *pri)
07855 {
07856 return pri->layer1_ignored;
07857 }
07858
07859 struct sig_pri_chan *sig_pri_chan_new(void *pvt_data, struct sig_pri_callback *callback, struct sig_pri_span *pri, int logicalspan, int channo, int trunkgroup)
07860 {
07861 struct sig_pri_chan *p;
07862
07863 p = ast_calloc(1, sizeof(*p));
07864 if (!p)
07865 return p;
07866
07867 p->logicalspan = logicalspan;
07868 p->prioffset = channo;
07869 p->mastertrunkgroup = trunkgroup;
07870
07871 p->calls = callback;
07872 p->chan_pvt = pvt_data;
07873
07874 p->pri = pri;
07875
07876 return p;
07877 }
07878
07879
07880
07881
07882
07883
07884
07885
07886
07887 void sig_pri_chan_delete(struct sig_pri_chan *doomed)
07888 {
07889 ast_free(doomed);
07890 }
07891
07892 #define SIG_PRI_SC_HEADER "%-4s %4s %-4s %-4s %-10s %-4s %s\n"
07893 #define SIG_PRI_SC_LINE "%4d %4d %-4s %-4s %-10s %-4s %s"
07894 void sig_pri_cli_show_channels_header(int fd)
07895 {
07896 ast_cli(fd, SIG_PRI_SC_HEADER, "PRI", "", "B", "Chan", "Call", "PRI", "Channel");
07897 ast_cli(fd, SIG_PRI_SC_HEADER, "Span", "Chan", "Chan", "Idle", "Level", "Call", "Name");
07898 }
07899
07900 void sig_pri_cli_show_channels(int fd, struct sig_pri_span *pri)
07901 {
07902 char line[256];
07903 int idx;
07904 struct sig_pri_chan *pvt;
07905
07906 ast_mutex_lock(&pri->lock);
07907 for (idx = 0; idx < pri->numchans; ++idx) {
07908 if (!pri->pvts[idx]) {
07909 continue;
07910 }
07911 pvt = pri->pvts[idx];
07912 sig_pri_lock_private(pvt);
07913 sig_pri_lock_owner(pri, idx);
07914 if (pvt->no_b_channel && sig_pri_is_chan_available(pvt)) {
07915
07916 sig_pri_unlock_private(pvt);
07917 continue;
07918 }
07919
07920 snprintf(line, sizeof(line), SIG_PRI_SC_LINE,
07921 pri->span,
07922 pvt->channel,
07923 pvt->no_b_channel ? "No" : "Yes",
07924 sig_pri_is_chan_available(pvt) ? "Yes" : "No",
07925 sig_pri_call_level2str(pvt->call_level),
07926 pvt->call ? "Yes" : "No",
07927 pvt->owner ? pvt->owner->name : "");
07928
07929 if (pvt->owner) {
07930 ast_channel_unlock(pvt->owner);
07931 }
07932 sig_pri_unlock_private(pvt);
07933
07934 ast_mutex_unlock(&pri->lock);
07935 ast_cli(fd, "%s\n", line);
07936 ast_mutex_lock(&pri->lock);
07937 }
07938 ast_mutex_unlock(&pri->lock);
07939 }
07940
07941 static void build_status(char *s, size_t len, int status, int active)
07942 {
07943 if (!s || len < 1) {
07944 return;
07945 }
07946 s[0] = '\0';
07947 if (!(status & DCHAN_NOTINALARM))
07948 strncat(s, "In Alarm, ", len - strlen(s) - 1);
07949 if (status & DCHAN_UP)
07950 strncat(s, "Up", len - strlen(s) - 1);
07951 else
07952 strncat(s, "Down", len - strlen(s) - 1);
07953 if (active)
07954 strncat(s, ", Active", len - strlen(s) - 1);
07955 else
07956 strncat(s, ", Standby", len - strlen(s) - 1);
07957 s[len - 1] = '\0';
07958 }
07959
07960 void sig_pri_cli_show_spans(int fd, int span, struct sig_pri_span *pri)
07961 {
07962 char status[256];
07963 int x;
07964 for (x = 0; x < SIG_PRI_NUM_DCHANS; x++) {
07965 if (pri->dchans[x]) {
07966 build_status(status, sizeof(status), pri->dchanavail[x], pri->dchans[x] == pri->pri);
07967 ast_cli(fd, "PRI span %d/%d: %s\n", span, x, status);
07968 }
07969 }
07970 }
07971
07972 void sig_pri_cli_show_span(int fd, int *dchannels, struct sig_pri_span *pri)
07973 {
07974 int x;
07975 char status[256];
07976
07977 for (x = 0; x < SIG_PRI_NUM_DCHANS; x++) {
07978 if (pri->dchans[x]) {
07979 #ifdef PRI_DUMP_INFO_STR
07980 char *info_str = NULL;
07981 #endif
07982 ast_cli(fd, "%s D-channel: %d\n", pri_order(x), dchannels[x]);
07983 build_status(status, sizeof(status), pri->dchanavail[x], pri->dchans[x] == pri->pri);
07984 ast_cli(fd, "Status: %s\n", status);
07985 ast_mutex_lock(&pri->lock);
07986 #ifdef PRI_DUMP_INFO_STR
07987 info_str = pri_dump_info_str(pri->pri);
07988 if (info_str) {
07989 ast_cli(fd, "%s", info_str);
07990 free(info_str);
07991 }
07992 #else
07993 pri_dump_info(pri->pri);
07994 #endif
07995 ast_mutex_unlock(&pri->lock);
07996 ast_cli(fd, "Overlap Recv: %s\n\n", (pri->overlapdial & DAHDI_OVERLAPDIAL_INCOMING)?"Yes":"No");
07997 ast_cli(fd, "\n");
07998 }
07999 }
08000 }
08001
08002 int pri_send_keypad_facility_exec(struct sig_pri_chan *p, const char *digits)
08003 {
08004 sig_pri_lock_private(p);
08005
08006 if (!p->pri || !p->call) {
08007 ast_debug(1, "Unable to find pri or call on channel!\n");
08008 sig_pri_unlock_private(p);
08009 return -1;
08010 }
08011
08012 pri_grab(p, p->pri);
08013 pri_keypad_facility(p->pri->pri, p->call, digits);
08014 pri_rel(p->pri);
08015
08016 sig_pri_unlock_private(p);
08017
08018 return 0;
08019 }
08020
08021 int pri_send_callrerouting_facility_exec(struct sig_pri_chan *p, enum ast_channel_state chanstate, const char *destination, const char *original, const char *reason)
08022 {
08023 int res;
08024
08025 sig_pri_lock_private(p);
08026
08027 if (!p->pri || !p->call) {
08028 ast_log(LOG_DEBUG, "Unable to find pri or call on channel!\n");
08029 sig_pri_unlock_private(p);
08030 return -1;
08031 }
08032
08033 pri_grab(p, p->pri);
08034 res = pri_callrerouting_facility(p->pri->pri, p->call, destination, original, reason);
08035 pri_rel(p->pri);
08036
08037 sig_pri_unlock_private(p);
08038
08039 return res;
08040 }
08041
08042 #if defined(HAVE_PRI_SERVICE_MESSAGES)
08043 int pri_maintenance_bservice(struct pri *pri, struct sig_pri_chan *p, int changestatus)
08044 {
08045 int channel = PVT_TO_CHANNEL(p);
08046 int span = PRI_SPAN(channel);
08047
08048 return pri_maintenance_service(pri, span, channel, changestatus);
08049 }
08050 #endif
08051
08052 void sig_pri_fixup(struct ast_channel *oldchan, struct ast_channel *newchan, struct sig_pri_chan *pchan)
08053 {
08054 if (pchan->owner == oldchan) {
08055 pchan->owner = newchan;
08056 }
08057 }
08058
08059 #if defined(HAVE_PRI_CCSS)
08060
08061
08062
08063
08064
08065
08066
08067
08068
08069
08070
08071
08072
08073
08074
08075
08076 int sig_pri_cc_agent_init(struct ast_cc_agent *agent, struct sig_pri_chan *pvt_chan)
08077 {
08078 struct sig_pri_cc_agent_prv *cc_pvt;
08079
08080 cc_pvt = ast_calloc(1, sizeof(*cc_pvt));
08081 if (!cc_pvt) {
08082 return -1;
08083 }
08084
08085 ast_mutex_lock(&pvt_chan->pri->lock);
08086 cc_pvt->pri = pvt_chan->pri;
08087 cc_pvt->cc_id = pri_cc_available(pvt_chan->pri->pri, pvt_chan->call);
08088 ast_mutex_unlock(&pvt_chan->pri->lock);
08089 if (cc_pvt->cc_id == -1) {
08090 ast_free(cc_pvt);
08091 return -1;
08092 }
08093 agent->private_data = cc_pvt;
08094 return 0;
08095 }
08096 #endif
08097
08098 #if defined(HAVE_PRI_CCSS)
08099
08100
08101
08102
08103
08104
08105
08106
08107
08108
08109
08110
08111
08112
08113
08114
08115
08116
08117
08118
08119
08120 int sig_pri_cc_agent_start_offer_timer(struct ast_cc_agent *agent)
08121 {
08122
08123 return 0;
08124 }
08125 #endif
08126
08127 #if defined(HAVE_PRI_CCSS)
08128
08129
08130
08131
08132
08133
08134
08135
08136
08137
08138
08139
08140
08141 int sig_pri_cc_agent_stop_offer_timer(struct ast_cc_agent *agent)
08142 {
08143
08144 return 0;
08145 }
08146 #endif
08147
08148 #if defined(HAVE_PRI_CCSS)
08149
08150
08151
08152
08153
08154
08155
08156
08157
08158
08159
08160
08161
08162
08163
08164
08165
08166
08167
08168
08169 void sig_pri_cc_agent_req_rsp(struct ast_cc_agent *agent, enum ast_cc_agent_response_reason reason)
08170 {
08171 struct sig_pri_cc_agent_prv *cc_pvt;
08172 int res;
08173 int status;
08174 const char *failed_msg;
08175 static const char *failed_to_send = "Failed to send the CC request response.";
08176 static const char *not_accepted = "The core declined the CC request.";
08177
08178 cc_pvt = agent->private_data;
08179 ast_mutex_lock(&cc_pvt->pri->lock);
08180 if (cc_pvt->cc_request_response_pending) {
08181 cc_pvt->cc_request_response_pending = 0;
08182
08183
08184 status = 2;
08185 switch (reason) {
08186 case AST_CC_AGENT_RESPONSE_SUCCESS:
08187 status = 0;
08188 break;
08189 case AST_CC_AGENT_RESPONSE_FAILURE_INVALID:
08190 status = 2;
08191 break;
08192 case AST_CC_AGENT_RESPONSE_FAILURE_TOO_MANY:
08193 status = 5;
08194 break;
08195 }
08196
08197 res = pri_cc_req_rsp(cc_pvt->pri->pri, cc_pvt->cc_id, status);
08198 if (!status) {
08199
08200 if (res) {
08201 failed_msg = failed_to_send;
08202 } else {
08203 failed_msg = NULL;
08204 }
08205 } else {
08206
08207 if (res) {
08208 failed_msg = failed_to_send;
08209 } else {
08210 failed_msg = not_accepted;
08211 }
08212 }
08213 } else {
08214 failed_msg = NULL;
08215 }
08216 ast_mutex_unlock(&cc_pvt->pri->lock);
08217 if (failed_msg) {
08218 ast_cc_failed(agent->core_id, "%s agent: %s", sig_pri_cc_type_name, failed_msg);
08219 }
08220 }
08221 #endif
08222
08223 #if defined(HAVE_PRI_CCSS)
08224
08225
08226
08227
08228
08229
08230
08231
08232
08233
08234
08235
08236
08237
08238
08239 int sig_pri_cc_agent_status_req(struct ast_cc_agent *agent)
08240 {
08241 struct sig_pri_cc_agent_prv *cc_pvt;
08242
08243 cc_pvt = agent->private_data;
08244 ast_mutex_lock(&cc_pvt->pri->lock);
08245 pri_cc_status_req(cc_pvt->pri->pri, cc_pvt->cc_id);
08246 ast_mutex_unlock(&cc_pvt->pri->lock);
08247 return 0;
08248 }
08249 #endif
08250
08251 #if defined(HAVE_PRI_CCSS)
08252
08253
08254
08255
08256
08257
08258
08259
08260
08261
08262
08263
08264
08265
08266
08267
08268
08269
08270
08271
08272
08273
08274 int sig_pri_cc_agent_stop_ringing(struct ast_cc_agent *agent)
08275 {
08276 struct sig_pri_cc_agent_prv *cc_pvt;
08277
08278 cc_pvt = agent->private_data;
08279 ast_mutex_lock(&cc_pvt->pri->lock);
08280 pri_cc_stop_alerting(cc_pvt->pri->pri, cc_pvt->cc_id);
08281 ast_mutex_unlock(&cc_pvt->pri->lock);
08282 return 0;
08283 }
08284 #endif
08285
08286 #if defined(HAVE_PRI_CCSS)
08287
08288
08289
08290
08291
08292
08293
08294
08295
08296
08297
08298
08299
08300
08301
08302
08303
08304
08305
08306
08307
08308 int sig_pri_cc_agent_party_b_free(struct ast_cc_agent *agent)
08309 {
08310 struct sig_pri_cc_agent_prv *cc_pvt;
08311
08312 cc_pvt = agent->private_data;
08313 ast_mutex_lock(&cc_pvt->pri->lock);
08314 pri_cc_b_free(cc_pvt->pri->pri, cc_pvt->cc_id);
08315 ast_mutex_unlock(&cc_pvt->pri->lock);
08316 return 0;
08317 }
08318 #endif
08319
08320 #if defined(HAVE_PRI_CCSS)
08321
08322
08323
08324
08325
08326
08327
08328
08329
08330
08331
08332
08333
08334
08335
08336
08337 int sig_pri_cc_agent_start_monitoring(struct ast_cc_agent *agent)
08338 {
08339
08340 return 0;
08341 }
08342 #endif
08343
08344 #if defined(HAVE_PRI_CCSS)
08345
08346
08347
08348
08349
08350
08351
08352
08353
08354
08355
08356
08357
08358
08359
08360
08361
08362
08363
08364 int sig_pri_cc_agent_callee_available(struct ast_cc_agent *agent)
08365 {
08366 struct sig_pri_cc_agent_prv *cc_pvt;
08367
08368 cc_pvt = agent->private_data;
08369 ast_mutex_lock(&cc_pvt->pri->lock);
08370 pri_cc_remote_user_free(cc_pvt->pri->pri, cc_pvt->cc_id);
08371 ast_mutex_unlock(&cc_pvt->pri->lock);
08372 return 0;
08373 }
08374 #endif
08375
08376 #if defined(HAVE_PRI_CCSS)
08377
08378
08379
08380
08381
08382
08383
08384
08385
08386
08387
08388
08389
08390
08391
08392
08393 void sig_pri_cc_agent_destructor(struct ast_cc_agent *agent)
08394 {
08395 struct sig_pri_cc_agent_prv *cc_pvt;
08396 int res;
08397
08398 cc_pvt = agent->private_data;
08399 if (!cc_pvt) {
08400
08401 return;
08402 }
08403 ast_mutex_lock(&cc_pvt->pri->lock);
08404 res = -1;
08405 if (cc_pvt->cc_request_response_pending) {
08406 res = pri_cc_req_rsp(cc_pvt->pri->pri, cc_pvt->cc_id, 2);
08407 }
08408 if (res) {
08409 pri_cc_cancel(cc_pvt->pri->pri, cc_pvt->cc_id);
08410 }
08411 ast_mutex_unlock(&cc_pvt->pri->lock);
08412 ast_free(cc_pvt);
08413 }
08414 #endif
08415
08416 #if defined(HAVE_PRI_CCSS)
08417
08418
08419
08420
08421
08422
08423
08424
08425
08426
08427 static int sig_pri_cc_monitor_instance_hash_fn(const void *obj, const int flags)
08428 {
08429 const struct sig_pri_cc_monitor_instance *monitor_instance = obj;
08430
08431 return monitor_instance->core_id;
08432 }
08433 #endif
08434
08435 #if defined(HAVE_PRI_CCSS)
08436
08437
08438
08439
08440
08441
08442
08443
08444
08445
08446
08447 static int sig_pri_cc_monitor_instance_cmp_fn(void *obj, void *arg, int flags)
08448 {
08449 struct sig_pri_cc_monitor_instance *monitor_1 = obj;
08450 struct sig_pri_cc_monitor_instance *monitor_2 = arg;
08451
08452 return monitor_1->core_id == monitor_2->core_id ? CMP_MATCH | CMP_STOP : 0;
08453 }
08454 #endif
08455
08456 #if defined(HAVE_PRI_CCSS)
08457
08458
08459
08460
08461
08462
08463
08464
08465
08466
08467
08468
08469
08470
08471
08472
08473
08474
08475 int sig_pri_cc_monitor_req_cc(struct ast_cc_monitor *monitor, int *available_timer_id)
08476 {
08477 struct sig_pri_cc_monitor_instance *instance;
08478 int cc_mode;
08479 int res;
08480
08481 switch (monitor->service_offered) {
08482 case AST_CC_CCBS:
08483 cc_mode = 0;
08484 break;
08485 case AST_CC_CCNR:
08486 cc_mode = 1;
08487 break;
08488 default:
08489
08490 return -1;
08491 }
08492
08493 instance = monitor->private_data;
08494
08495
08496 ast_mutex_lock(&instance->pri->lock);
08497 res = pri_cc_req(instance->pri->pri, instance->cc_id, cc_mode);
08498 ast_mutex_unlock(&instance->pri->lock);
08499
08500 return res;
08501 }
08502 #endif
08503
08504 #if defined(HAVE_PRI_CCSS)
08505
08506
08507
08508
08509
08510
08511
08512
08513
08514
08515
08516
08517
08518 int sig_pri_cc_monitor_suspend(struct ast_cc_monitor *monitor)
08519 {
08520 struct sig_pri_cc_monitor_instance *instance;
08521
08522 instance = monitor->private_data;
08523 ast_mutex_lock(&instance->pri->lock);
08524 pri_cc_status(instance->pri->pri, instance->cc_id, 1);
08525 ast_mutex_unlock(&instance->pri->lock);
08526
08527 return 0;
08528 }
08529 #endif
08530
08531 #if defined(HAVE_PRI_CCSS)
08532
08533
08534
08535
08536
08537
08538
08539
08540
08541
08542
08543
08544 int sig_pri_cc_monitor_unsuspend(struct ast_cc_monitor *monitor)
08545 {
08546 struct sig_pri_cc_monitor_instance *instance;
08547
08548 instance = monitor->private_data;
08549 ast_mutex_lock(&instance->pri->lock);
08550 pri_cc_status(instance->pri->pri, instance->cc_id, 0);
08551 ast_mutex_unlock(&instance->pri->lock);
08552
08553 return 0;
08554 }
08555 #endif
08556
08557 #if defined(HAVE_PRI_CCSS)
08558
08559
08560
08561
08562
08563
08564
08565
08566
08567
08568
08569
08570
08571
08572
08573
08574 int sig_pri_cc_monitor_status_rsp(struct ast_cc_monitor *monitor, enum ast_device_state devstate)
08575 {
08576 struct sig_pri_cc_monitor_instance *instance;
08577 int cc_status;
08578
08579 switch (devstate) {
08580 case AST_DEVICE_UNKNOWN:
08581 case AST_DEVICE_NOT_INUSE:
08582 cc_status = 0;
08583 break;
08584 case AST_DEVICE_BUSY:
08585 case AST_DEVICE_INUSE:
08586 cc_status = 1;
08587 break;
08588 default:
08589
08590 return 0;
08591 }
08592 instance = monitor->private_data;
08593 ast_mutex_lock(&instance->pri->lock);
08594 pri_cc_status_req_rsp(instance->pri->pri, instance->cc_id, cc_status);
08595 ast_mutex_unlock(&instance->pri->lock);
08596
08597 return 0;
08598 }
08599 #endif
08600
08601 #if defined(HAVE_PRI_CCSS)
08602
08603
08604
08605
08606
08607
08608
08609
08610
08611
08612
08613
08614
08615
08616
08617
08618
08619 int sig_pri_cc_monitor_cancel_available_timer(struct ast_cc_monitor *monitor, int *sched_id)
08620 {
08621
08622
08623
08624
08625
08626 return 0;
08627 }
08628 #endif
08629
08630 #if defined(HAVE_PRI_CCSS)
08631
08632
08633
08634
08635
08636
08637
08638
08639
08640
08641
08642 void sig_pri_cc_monitor_destructor(void *monitor_pvt)
08643 {
08644 struct sig_pri_cc_monitor_instance *instance;
08645
08646 instance = monitor_pvt;
08647 if (!instance) {
08648 return;
08649 }
08650 ao2_unlink(sig_pri_cc_monitors, instance);
08651 ao2_ref(instance, -1);
08652 }
08653 #endif
08654
08655
08656
08657
08658
08659
08660
08661
08662
08663
08664 int sig_pri_load(const char *cc_type_name)
08665 {
08666 #if defined(HAVE_PRI_CCSS)
08667 sig_pri_cc_type_name = cc_type_name;
08668 sig_pri_cc_monitors = ao2_container_alloc(37, sig_pri_cc_monitor_instance_hash_fn,
08669 sig_pri_cc_monitor_instance_cmp_fn);
08670 if (!sig_pri_cc_monitors) {
08671 return -1;
08672 }
08673 #endif
08674 return 0;
08675 }
08676
08677
08678
08679
08680
08681
08682
08683 void sig_pri_unload(void)
08684 {
08685 #if defined(HAVE_PRI_CCSS)
08686 if (sig_pri_cc_monitors) {
08687 ao2_ref(sig_pri_cc_monitors, -1);
08688 sig_pri_cc_monitors = NULL;
08689 }
08690 #endif
08691 }
08692
08693 #endif