00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "isdn_lib_intern.h"
00024
00025
00026 #include "isdn_lib.h"
00027
00028 #include "ie.c"
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042 static void build_display_str(char *display, size_t display_length, int display_format, const char *name, const char *number)
00043 {
00044 display[0] = 0;
00045 switch (display_format) {
00046 default:
00047 case 0:
00048 break;
00049
00050 case 1:
00051 snprintf(display, display_length, "%s", name);
00052 break;
00053
00054 case 2:
00055 snprintf(display, display_length, "%s", number);
00056 break;
00057
00058 case 3:
00059 if (name[0] || number[0]) {
00060 snprintf(display, display_length, "\"%s\" <%s>", name, number);
00061 }
00062 break;
00063 }
00064 }
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077 static void enc_ie_facility(unsigned char **ntmode, msg_t *msg, struct FacParm *fac, int nt)
00078 {
00079 int len;
00080 Q931_info_t *qi;
00081 unsigned char *p;
00082 unsigned char buf[256];
00083
00084 len = encodeFac(buf, fac);
00085 if (len <= 0) {
00086
00087
00088
00089
00090 fac->Function = Fac_None;
00091 return;
00092 }
00093
00094 p = msg_put(msg, len);
00095 if (nt) {
00096 *ntmode = p + 1;
00097 } else {
00098 qi = (Q931_info_t *) (msg->data + mISDN_HEADER_LEN);
00099 qi->QI_ELEMENT(facility) = p - (unsigned char *) qi - sizeof(Q931_info_t);
00100 }
00101
00102 memcpy(p, buf, len);
00103
00104
00105 fac->Function = Fac_None;
00106 }
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120 static void dec_ie_facility(unsigned char *p, Q931_info_t *qi, struct FacParm *fac, int nt, struct misdn_bchannel *bc)
00121 {
00122 fac->Function = Fac_None;
00123
00124 if (!nt) {
00125 p = NULL;
00126 if (qi->QI_ELEMENT(facility)) {
00127 p = (unsigned char *) qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(facility) + 1;
00128 }
00129 }
00130 if (!p) {
00131 return;
00132 }
00133
00134 if (decodeFac(p, fac)) {
00135 cb_log(3, bc->port, "Decoding facility ie failed! Unrecognized facility message?\n");
00136 }
00137 }
00138
00139
00140
00141 static void set_channel(struct misdn_bchannel *bc, int channel)
00142 {
00143
00144 cb_log(3,bc->port,"set_channel: bc->channel:%d channel:%d\n", bc->channel, channel);
00145
00146
00147 if (channel==0xff) {
00148
00149 channel=-1;
00150 }
00151
00152
00153 if (channel > 0 && bc->nt ) {
00154
00155 if (bc->channel && ( bc->channel != 0xff) ) {
00156 cb_log(0,bc->port,"We already have a channel (%d)\n", bc->channel);
00157 } else {
00158 bc->channel = channel;
00159 cb_event(EVENT_NEW_CHANNEL,bc,NULL);
00160 }
00161 }
00162
00163 if (channel > 0 && !bc->nt ) {
00164 bc->channel = channel;
00165 cb_event(EVENT_NEW_CHANNEL,bc,NULL);
00166 }
00167 }
00168
00169 static void parse_proceeding (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00170 {
00171 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00172 CALL_PROCEEDING_t *proceeding = (CALL_PROCEEDING_t *) (msg->data + HEADER_LEN);
00173
00174
00175 {
00176 int exclusive, channel;
00177 dec_ie_channel_id(proceeding->CHANNEL_ID, (Q931_info_t *)proceeding, &exclusive, &channel, nt,bc);
00178
00179 set_channel(bc,channel);
00180
00181 }
00182
00183 dec_ie_progress(proceeding->PROGRESS, (Q931_info_t *)proceeding, &bc->progress_coding, &bc->progress_location, &bc->progress_indicator, nt, bc);
00184
00185 dec_ie_facility(proceeding->FACILITY, (Q931_info_t *) proceeding, &bc->fac_in, nt, bc);
00186
00187
00188
00189 #ifdef DEBUG
00190 printf("Parsing PROCEEDING Msg\n");
00191 #endif
00192 }
00193 static msg_t *build_proceeding (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00194 {
00195 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00196 CALL_PROCEEDING_t *proceeding;
00197 msg_t *msg =(msg_t*)create_l3msg(CC_PROCEEDING | REQUEST, MT_CALL_PROCEEDING, bc?bc->l3_id:-1, sizeof(CALL_PROCEEDING_t) ,nt);
00198
00199 proceeding=(CALL_PROCEEDING_t*)((msg->data+HEADER_LEN));
00200
00201 enc_ie_channel_id(&proceeding->CHANNEL_ID, msg, 1,bc->channel, nt,bc);
00202
00203 if (nt)
00204 enc_ie_progress(&proceeding->PROGRESS, msg, 0, nt?1:5, 8, nt,bc);
00205
00206 if (bc->fac_out.Function != Fac_None) {
00207 enc_ie_facility(&proceeding->FACILITY, msg, &bc->fac_out, nt);
00208 }
00209
00210
00211
00212 #ifdef DEBUG
00213 printf("Building PROCEEDING Msg\n");
00214 #endif
00215 return msg;
00216 }
00217
00218 static void parse_alerting (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00219 {
00220 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00221 ALERTING_t *alerting = (ALERTING_t *) (msg->data + HEADER_LEN);
00222
00223
00224 dec_ie_facility(alerting->FACILITY, (Q931_info_t *) alerting, &bc->fac_in, nt, bc);
00225
00226
00227
00228 dec_ie_progress(alerting->PROGRESS, (Q931_info_t *)alerting, &bc->progress_coding, &bc->progress_location, &bc->progress_indicator, nt, bc);
00229
00230 #ifdef DEBUG
00231 printf("Parsing ALERTING Msg\n");
00232 #endif
00233
00234
00235 }
00236
00237 static msg_t *build_alerting (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00238 {
00239 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00240 ALERTING_t *alerting;
00241 msg_t *msg =(msg_t*)create_l3msg(CC_ALERTING | REQUEST, MT_ALERTING, bc?bc->l3_id:-1, sizeof(ALERTING_t) ,nt);
00242
00243 alerting=(ALERTING_t*)((msg->data+HEADER_LEN));
00244
00245 enc_ie_channel_id(&alerting->CHANNEL_ID, msg, 1,bc->channel, nt,bc);
00246
00247 if (nt)
00248 enc_ie_progress(&alerting->PROGRESS, msg, 0, nt?1:5, 8, nt,bc);
00249
00250 if (bc->fac_out.Function != Fac_None) {
00251 enc_ie_facility(&alerting->FACILITY, msg, &bc->fac_out, nt);
00252 }
00253
00254
00255
00256 #ifdef DEBUG
00257 printf("Building ALERTING Msg\n");
00258 #endif
00259 return msg;
00260 }
00261
00262
00263 static void parse_progress (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00264 {
00265 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00266 PROGRESS_t *progress = (PROGRESS_t *) (msg->data + HEADER_LEN);
00267
00268
00269 dec_ie_progress(progress->PROGRESS, (Q931_info_t *)progress, &bc->progress_coding, &bc->progress_location, &bc->progress_indicator, nt, bc);
00270
00271 dec_ie_facility(progress->FACILITY, (Q931_info_t *) progress, &bc->fac_in, nt, bc);
00272
00273 #ifdef DEBUG
00274 printf("Parsing PROGRESS Msg\n");
00275 #endif
00276 }
00277
00278 static msg_t *build_progress (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00279 {
00280 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00281 PROGRESS_t *progress;
00282 msg_t *msg =(msg_t*)create_l3msg(CC_PROGRESS | REQUEST, MT_PROGRESS, bc?bc->l3_id:-1, sizeof(PROGRESS_t) ,nt);
00283
00284 progress=(PROGRESS_t*)((msg->data+HEADER_LEN));
00285
00286 enc_ie_progress(&progress->PROGRESS, msg, 0, nt ? 1 : 5, 8, nt, bc);
00287
00288 if (bc->fac_out.Function != Fac_None) {
00289 enc_ie_facility(&progress->FACILITY, msg, &bc->fac_out, nt);
00290 }
00291
00292 #ifdef DEBUG
00293 printf("Building PROGRESS Msg\n");
00294 #endif
00295 return msg;
00296 }
00297
00298 #if defined(AST_MISDN_ENHANCEMENTS)
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308
00309 static void extract_setup_Bc_Hlc_Llc(SETUP_t *setup, int nt, struct misdn_bchannel *bc)
00310 {
00311 __u8 *p;
00312 Q931_info_t *qi;
00313
00314 qi = (Q931_info_t *) setup;
00315
00316
00317 if (nt) {
00318 p = (__u8 *) setup->BEARER;
00319 } else {
00320 if (qi->QI_ELEMENT(bearer_capability)) {
00321 p = (__u8 *) qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(bearer_capability) + 1;
00322 } else {
00323 p = NULL;
00324 }
00325 }
00326 if (!p || *p == 0 || sizeof(bc->setup_bc_hlc_llc.Bc.Contents) < *p) {
00327 bc->setup_bc_hlc_llc.Bc.Length = 0;
00328 } else {
00329 bc->setup_bc_hlc_llc.Bc.Length = *p;
00330 memcpy(bc->setup_bc_hlc_llc.Bc.Contents, p + 1, *p);
00331 }
00332
00333
00334 if (nt) {
00335 p = (__u8 *) setup->LLC;
00336 } else {
00337 if (qi->QI_ELEMENT(llc)) {
00338 p = (__u8 *) qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(llc) + 1;
00339 } else {
00340 p = NULL;
00341 }
00342 }
00343 if (!p || *p == 0 || sizeof(bc->setup_bc_hlc_llc.Llc.Contents) < *p) {
00344 bc->setup_bc_hlc_llc.Llc.Length = 0;
00345 } else {
00346 bc->setup_bc_hlc_llc.Llc.Length = *p;
00347 memcpy(bc->setup_bc_hlc_llc.Llc.Contents, p + 1, *p);
00348 }
00349
00350
00351 if (nt) {
00352 p = (__u8 *) setup->HLC;
00353 } else {
00354 if (qi->QI_ELEMENT(hlc)) {
00355 p = (__u8 *) qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(hlc) + 1;
00356 } else {
00357 p = NULL;
00358 }
00359 }
00360 if (!p || *p == 0 || sizeof(bc->setup_bc_hlc_llc.Hlc.Contents) < *p) {
00361 bc->setup_bc_hlc_llc.Hlc.Length = 0;
00362 } else {
00363 bc->setup_bc_hlc_llc.Hlc.Length = *p;
00364 memcpy(bc->setup_bc_hlc_llc.Hlc.Contents, p + 1, *p);
00365 }
00366 }
00367 #endif
00368
00369 static void parse_setup (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00370 {
00371 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00372 SETUP_t *setup = (SETUP_t *) (msg->data + HEADER_LEN);
00373 Q931_info_t *qi = (Q931_info_t *) (msg->data + HEADER_LEN);
00374 int type;
00375 int plan;
00376 int present;
00377 int screen;
00378 int reason;
00379
00380 #ifdef DEBUG
00381 printf("Parsing SETUP Msg\n");
00382 #endif
00383
00384 dec_ie_calling_pn(setup->CALLING_PN, qi, &type, &plan, &present, &screen, bc->caller.number, sizeof(bc->caller.number), nt, bc);
00385 bc->caller.number_type = type;
00386 bc->caller.number_plan = plan;
00387 switch (present) {
00388 default:
00389 case 0:
00390 bc->caller.presentation = 0;
00391 break;
00392 case 1:
00393 bc->caller.presentation = 1;
00394 break;
00395 case 2:
00396 bc->caller.presentation = 2;
00397 break;
00398 }
00399 if (0 <= screen) {
00400 bc->caller.screening = screen;
00401 } else {
00402 bc->caller.screening = 0;
00403 }
00404
00405 dec_ie_facility(setup->FACILITY, (Q931_info_t *) setup, &bc->fac_in, nt, bc);
00406
00407 dec_ie_called_pn(setup->CALLED_PN, (Q931_info_t *) setup, &type, &plan, bc->dialed.number, sizeof(bc->dialed.number), nt, bc);
00408 bc->dialed.number_type = type;
00409 bc->dialed.number_plan = plan;
00410
00411 dec_ie_keypad(setup->KEYPAD, (Q931_info_t *) setup, bc->keypad, sizeof(bc->keypad), nt, bc);
00412
00413 dec_ie_complete(setup->COMPLETE, (Q931_info_t *) setup, &bc->sending_complete, nt, bc);
00414
00415 dec_ie_redir_nr(setup->REDIR_NR, (Q931_info_t *) setup, &type, &plan, &present, &screen, &reason, bc->redirecting.from.number, sizeof(bc->redirecting.from.number), nt, bc);
00416 bc->redirecting.from.number_type = type;
00417 bc->redirecting.from.number_plan = plan;
00418 switch (present) {
00419 default:
00420 case 0:
00421 bc->redirecting.from.presentation = 0;
00422 break;
00423 case 1:
00424 bc->redirecting.from.presentation = 1;
00425 break;
00426 case 2:
00427 bc->redirecting.from.presentation = 2;
00428 break;
00429 }
00430 if (0 <= screen) {
00431 bc->redirecting.from.screening = screen;
00432 } else {
00433 bc->redirecting.from.screening = 0;
00434 }
00435 if (0 <= reason) {
00436 bc->redirecting.reason = reason;
00437 } else {
00438 bc->redirecting.reason = mISDN_REDIRECTING_REASON_UNKNOWN;
00439 }
00440
00441 {
00442 int coding, capability, mode, rate, multi, user, async, urate, stopbits, dbits, parity;
00443
00444 dec_ie_bearer(setup->BEARER, (Q931_info_t *)setup, &coding, &capability, &mode, &rate, &multi, &user, &async, &urate, &stopbits, &dbits, &parity, nt,bc);
00445 switch (capability) {
00446 case -1: bc->capability=INFO_CAPABILITY_DIGITAL_UNRESTRICTED;
00447 break;
00448 case 0: bc->capability=INFO_CAPABILITY_SPEECH;
00449 break;
00450 case 18: bc->capability=INFO_CAPABILITY_VIDEO;
00451 break;
00452 case 8: bc->capability=INFO_CAPABILITY_DIGITAL_UNRESTRICTED;
00453 bc->user1 = user;
00454 bc->urate = urate;
00455
00456 bc->rate = rate;
00457 bc->mode = mode;
00458 break;
00459 case 9: bc->capability=INFO_CAPABILITY_DIGITAL_RESTRICTED;
00460 break;
00461 default:
00462 break;
00463 }
00464
00465 switch(user) {
00466 case 2:
00467 bc->law=INFO_CODEC_ULAW;
00468 break;
00469 case 3:
00470 bc->law=INFO_CODEC_ALAW;
00471 break;
00472 default:
00473 bc->law=INFO_CODEC_ALAW;
00474
00475 }
00476
00477 bc->capability=capability;
00478 }
00479 {
00480 int exclusive, channel;
00481 dec_ie_channel_id(setup->CHANNEL_ID, (Q931_info_t *)setup, &exclusive, &channel, nt,bc);
00482
00483 set_channel(bc,channel);
00484 }
00485
00486 {
00487 int protocol ;
00488 dec_ie_useruser(setup->USER_USER, (Q931_info_t *)setup, &protocol, bc->uu, &bc->uulen, nt,bc);
00489 if (bc->uulen) cb_log(1, bc->port, "USERUSERINFO:%s\n", bc->uu);
00490 else
00491 cb_log(1, bc->port, "NO USERUSERINFO\n");
00492 }
00493
00494 dec_ie_progress(setup->PROGRESS, (Q931_info_t *)setup, &bc->progress_coding, &bc->progress_location, &bc->progress_indicator, nt, bc);
00495
00496 #if defined(AST_MISDN_ENHANCEMENTS)
00497 extract_setup_Bc_Hlc_Llc(setup, nt, bc);
00498 #endif
00499 }
00500
00501 #define ANY_CHANNEL 0xff
00502 static msg_t *build_setup (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00503 {
00504 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00505 SETUP_t *setup;
00506 msg_t *msg =(msg_t*)create_l3msg(CC_SETUP | REQUEST, MT_SETUP, bc?bc->l3_id:-1, sizeof(SETUP_t) ,nt);
00507 int is_ptp;
00508 enum FacFunction fac_type;
00509
00510 setup=(SETUP_t*)((msg->data+HEADER_LEN));
00511
00512 if (bc->channel == 0 || bc->channel == ANY_CHANNEL || bc->channel==-1)
00513 enc_ie_channel_id(&setup->CHANNEL_ID, msg, 0, bc->channel, nt,bc);
00514 else
00515 enc_ie_channel_id(&setup->CHANNEL_ID, msg, 1, bc->channel, nt,bc);
00516
00517 fac_type = bc->fac_out.Function;
00518 if (fac_type != Fac_None) {
00519 enc_ie_facility(&setup->FACILITY, msg, &bc->fac_out, nt);
00520 }
00521
00522 enc_ie_calling_pn(&setup->CALLING_PN, msg, bc->caller.number_type, bc->caller.number_plan,
00523 bc->caller.presentation, bc->caller.screening, bc->caller.number, nt, bc);
00524
00525 if (bc->dialed.number[0]) {
00526 enc_ie_called_pn(&setup->CALLED_PN, msg, bc->dialed.number_type, bc->dialed.number_plan, bc->dialed.number, nt, bc);
00527 }
00528
00529 switch (bc->outgoing_colp) {
00530 case 0:
00531 case 1:
00532 is_ptp = misdn_lib_is_ptp(bc->port);
00533 if (bc->redirecting.from.number[0]
00534 && ((!is_ptp && nt)
00535 || (is_ptp
00536 #if defined(AST_MISDN_ENHANCEMENTS)
00537
00538
00539
00540
00541
00542
00543 && fac_type != Fac_DivertingLegInformation2
00544 #endif
00545 ))) {
00546 #if 1
00547
00548 enc_ie_redir_nr(&setup->REDIR_NR, msg, bc->redirecting.from.number_type,
00549 bc->redirecting.from.number_plan, bc->redirecting.from.presentation, 0,
00550 bc->redirecting.reason, bc->redirecting.from.number, nt, bc);
00551 #else
00552
00553 enc_ie_redir_nr(&setup->REDIR_NR, msg, bc->redirecting.from.number_type,
00554 bc->redirecting.from.number_plan, bc->redirecting.from.presentation,
00555 bc->redirecting.from.screening, bc->redirecting.reason,
00556 bc->redirecting.from.number, nt, bc);
00557 #endif
00558 }
00559 break;
00560 default:
00561 break;
00562 }
00563
00564 if (bc->keypad[0]) {
00565 enc_ie_keypad(&setup->KEYPAD, msg, bc->keypad, nt,bc);
00566 }
00567
00568
00569
00570 if (*bc->display) {
00571 enc_ie_display(&setup->DISPLAY, msg, bc->display, nt, bc);
00572 } else if (nt && bc->caller.presentation == 0) {
00573 char display[sizeof(bc->display)];
00574
00575
00576 build_display_str(display, sizeof(display), bc->display_setup, bc->caller.name, bc->caller.number);
00577 if (display[0]) {
00578 enc_ie_display(&setup->DISPLAY, msg, display, nt, bc);
00579 }
00580 }
00581
00582 {
00583 int coding = 0;
00584 int capability;
00585 int mode = 0;
00586 int user;
00587 int rate = 0x10;
00588
00589 switch (bc->law) {
00590 case INFO_CODEC_ULAW: user=2;
00591 break;
00592 case INFO_CODEC_ALAW: user=3;
00593 break;
00594 default:
00595 user=3;
00596 }
00597
00598 switch (bc->capability) {
00599 case INFO_CAPABILITY_SPEECH: capability = 0;
00600 break;
00601 case INFO_CAPABILITY_DIGITAL_UNRESTRICTED: capability = 8;
00602 user=-1;
00603 mode=bc->mode;
00604 rate=bc->rate;
00605 break;
00606 case INFO_CAPABILITY_DIGITAL_RESTRICTED: capability = 9;
00607 user=-1;
00608 break;
00609 default:
00610 capability=bc->capability;
00611 }
00612
00613 enc_ie_bearer(&setup->BEARER, msg, coding, capability, mode, rate, -1, user, nt,bc);
00614 }
00615
00616 if (bc->sending_complete) {
00617 enc_ie_complete(&setup->COMPLETE,msg, bc->sending_complete, nt, bc);
00618 }
00619
00620 if (bc->uulen) {
00621 int protocol=4;
00622 enc_ie_useruser(&setup->USER_USER, msg, protocol, bc->uu, bc->uulen, nt,bc);
00623 cb_log(1, bc->port, "ENCODING USERUSERINFO:%s\n", bc->uu);
00624 }
00625
00626 #if defined(AST_MISDN_ENHANCEMENTS)
00627 extract_setup_Bc_Hlc_Llc(setup, nt, bc);
00628 #endif
00629
00630 #ifdef DEBUG
00631 printf("Building SETUP Msg\n");
00632 #endif
00633 return msg;
00634 }
00635
00636 static void parse_connect (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00637 {
00638 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00639 CONNECT_t *connect = (CONNECT_t *) (msg->data + HEADER_LEN);
00640 int type;
00641 int plan;
00642 int pres;
00643 int screen;
00644
00645 bc->ces = connect->ces;
00646
00647 dec_ie_progress(connect->PROGRESS, (Q931_info_t *)connect, &bc->progress_coding, &bc->progress_location, &bc->progress_indicator, nt, bc);
00648
00649 dec_ie_connected_pn(connect->CONNECT_PN, (Q931_info_t *) connect, &type, &plan,
00650 &pres, &screen, bc->connected.number, sizeof(bc->connected.number), nt, bc);
00651 bc->connected.number_type = type;
00652 bc->connected.number_plan = plan;
00653 switch (pres) {
00654 default:
00655 case 0:
00656 bc->connected.presentation = 0;
00657 break;
00658 case 1:
00659 bc->connected.presentation = 1;
00660 break;
00661 case 2:
00662 bc->connected.presentation = 2;
00663 break;
00664 }
00665 if (0 <= screen) {
00666 bc->connected.screening = screen;
00667 } else {
00668 bc->connected.screening = 0;
00669 }
00670
00671 dec_ie_facility(connect->FACILITY, (Q931_info_t *) connect, &bc->fac_in, nt, bc);
00672
00673
00674
00675
00676
00677 #ifdef DEBUG
00678 printf("Parsing CONNECT Msg\n");
00679 #endif
00680 }
00681
00682 static msg_t *build_connect (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00683 {
00684 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00685 CONNECT_t *connect;
00686 msg_t *msg =(msg_t*)create_l3msg(CC_CONNECT | REQUEST, MT_CONNECT, bc?bc->l3_id:-1, sizeof(CONNECT_t) ,nt);
00687
00688 cb_log(6,bc->port,"BUILD_CONNECT: bc:%p bc->l3id:%d, nt:%d\n",bc,bc->l3_id,nt);
00689
00690 connect=(CONNECT_t*)((msg->data+HEADER_LEN));
00691
00692 if (nt) {
00693 time_t now;
00694 time(&now);
00695 enc_ie_date(&connect->DATE, msg, now, nt,bc);
00696 }
00697
00698 switch (bc->outgoing_colp) {
00699 case 0:
00700 case 1:
00701 enc_ie_connected_pn(&connect->CONNECT_PN, msg, bc->connected.number_type,
00702 bc->connected.number_plan, bc->connected.presentation,
00703 bc->connected.screening, bc->connected.number, nt, bc);
00704 break;
00705 default:
00706 break;
00707 }
00708
00709 if (nt && bc->connected.presentation == 0) {
00710 char display[sizeof(bc->display)];
00711
00712
00713 build_display_str(display, sizeof(display), bc->display_connected, bc->connected.name, bc->connected.number);
00714 if (display[0]) {
00715 enc_ie_display(&connect->DISPLAY, msg, display, nt, bc);
00716 }
00717 }
00718
00719 if (bc->fac_out.Function != Fac_None) {
00720 enc_ie_facility(&connect->FACILITY, msg, &bc->fac_out, nt);
00721 }
00722
00723 #ifdef DEBUG
00724 printf("Building CONNECT Msg\n");
00725 #endif
00726 return msg;
00727 }
00728
00729 static void parse_setup_acknowledge (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00730 {
00731 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00732 SETUP_ACKNOWLEDGE_t *setup_acknowledge = (SETUP_ACKNOWLEDGE_t *) (msg->data + HEADER_LEN);
00733
00734 {
00735 int exclusive, channel;
00736 dec_ie_channel_id(setup_acknowledge->CHANNEL_ID, (Q931_info_t *)setup_acknowledge, &exclusive, &channel, nt,bc);
00737
00738
00739 set_channel(bc, channel);
00740 }
00741
00742 dec_ie_progress(setup_acknowledge->PROGRESS, (Q931_info_t *)setup_acknowledge, &bc->progress_coding, &bc->progress_location, &bc->progress_indicator, nt, bc);
00743
00744 dec_ie_facility(setup_acknowledge->FACILITY, (Q931_info_t *) setup_acknowledge, &bc->fac_in, nt, bc);
00745
00746 #ifdef DEBUG
00747 printf("Parsing SETUP_ACKNOWLEDGE Msg\n");
00748 #endif
00749
00750
00751 }
00752
00753 static msg_t *build_setup_acknowledge (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00754 {
00755 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00756 SETUP_ACKNOWLEDGE_t *setup_acknowledge;
00757 msg_t *msg =(msg_t*)create_l3msg(CC_SETUP_ACKNOWLEDGE | REQUEST, MT_SETUP_ACKNOWLEDGE, bc?bc->l3_id:-1, sizeof(SETUP_ACKNOWLEDGE_t) ,nt);
00758
00759 setup_acknowledge=(SETUP_ACKNOWLEDGE_t*)((msg->data+HEADER_LEN));
00760
00761 enc_ie_channel_id(&setup_acknowledge->CHANNEL_ID, msg, 1,bc->channel, nt,bc);
00762
00763 if (nt)
00764 enc_ie_progress(&setup_acknowledge->PROGRESS, msg, 0, nt?1:5, 8, nt,bc);
00765
00766 if (bc->fac_out.Function != Fac_None) {
00767 enc_ie_facility(&setup_acknowledge->FACILITY, msg, &bc->fac_out, nt);
00768 }
00769
00770 #ifdef DEBUG
00771 printf("Building SETUP_ACKNOWLEDGE Msg\n");
00772 #endif
00773 return msg;
00774 }
00775
00776 static void parse_connect_acknowledge (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00777 {
00778 #ifdef DEBUG
00779 printf("Parsing CONNECT_ACKNOWLEDGE Msg\n");
00780 #endif
00781
00782
00783 }
00784
00785 static msg_t *build_connect_acknowledge (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00786 {
00787 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
00788 CONNECT_ACKNOWLEDGE_t *connect_acknowledge;
00789 msg_t *msg =(msg_t*)create_l3msg(CC_CONNECT | RESPONSE, MT_CONNECT, bc?bc->l3_id:-1, sizeof(CONNECT_ACKNOWLEDGE_t) ,nt);
00790
00791 connect_acknowledge=(CONNECT_ACKNOWLEDGE_t*)((msg->data+HEADER_LEN));
00792
00793 enc_ie_channel_id(&connect_acknowledge->CHANNEL_ID, msg, 1, bc->channel, nt,bc);
00794
00795 #ifdef DEBUG
00796 printf("Building CONNECT_ACKNOWLEDGE Msg\n");
00797 #endif
00798 return msg;
00799 }
00800
00801 static void parse_user_information (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00802 {
00803 #ifdef DEBUG
00804 printf("Parsing USER_INFORMATION Msg\n");
00805 #endif
00806
00807
00808 }
00809
00810 static msg_t *build_user_information (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00811 {
00812 msg_t *msg =(msg_t*)create_l3msg(CC_USER_INFORMATION | REQUEST, MT_USER_INFORMATION, bc?bc->l3_id:-1, sizeof(USER_INFORMATION_t) ,nt);
00813
00814 #ifdef DEBUG
00815 printf("Building USER_INFORMATION Msg\n");
00816 #endif
00817 return msg;
00818 }
00819
00820 static void parse_suspend_reject (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00821 {
00822 #ifdef DEBUG
00823 printf("Parsing SUSPEND_REJECT Msg\n");
00824 #endif
00825
00826
00827 }
00828
00829 static msg_t *build_suspend_reject (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00830 {
00831 msg_t *msg =(msg_t*)create_l3msg(CC_SUSPEND_REJECT | REQUEST, MT_SUSPEND_REJECT, bc?bc->l3_id:-1, sizeof(SUSPEND_REJECT_t) ,nt);
00832
00833 #ifdef DEBUG
00834 printf("Building SUSPEND_REJECT Msg\n");
00835 #endif
00836 return msg;
00837 }
00838
00839 static void parse_resume_reject (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00840 {
00841 #ifdef DEBUG
00842 printf("Parsing RESUME_REJECT Msg\n");
00843 #endif
00844
00845
00846 }
00847
00848 static msg_t *build_resume_reject (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00849 {
00850 msg_t *msg =(msg_t*)create_l3msg(CC_RESUME_REJECT | REQUEST, MT_RESUME_REJECT, bc?bc->l3_id:-1, sizeof(RESUME_REJECT_t) ,nt);
00851
00852 #ifdef DEBUG
00853 printf("Building RESUME_REJECT Msg\n");
00854 #endif
00855 return msg;
00856 }
00857
00858 static void parse_hold (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00859 {
00860 #ifdef DEBUG
00861 printf("Parsing HOLD Msg\n");
00862 #endif
00863
00864
00865 }
00866
00867 static msg_t *build_hold (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00868 {
00869 msg_t *msg =(msg_t*)create_l3msg(CC_HOLD | REQUEST, MT_HOLD, bc?bc->l3_id:-1, sizeof(HOLD_t) ,nt);
00870
00871 #ifdef DEBUG
00872 printf("Building HOLD Msg\n");
00873 #endif
00874 return msg;
00875 }
00876
00877 static void parse_suspend (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00878 {
00879 #ifdef DEBUG
00880 printf("Parsing SUSPEND Msg\n");
00881 #endif
00882
00883
00884 }
00885
00886 static msg_t *build_suspend (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00887 {
00888 msg_t *msg =(msg_t*)create_l3msg(CC_SUSPEND | REQUEST, MT_SUSPEND, bc?bc->l3_id:-1, sizeof(SUSPEND_t) ,nt);
00889
00890 #ifdef DEBUG
00891 printf("Building SUSPEND Msg\n");
00892 #endif
00893 return msg;
00894 }
00895
00896 static void parse_resume (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00897 {
00898 #ifdef DEBUG
00899 printf("Parsing RESUME Msg\n");
00900 #endif
00901
00902
00903 }
00904
00905 static msg_t *build_resume (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00906 {
00907 msg_t *msg =(msg_t*)create_l3msg(CC_RESUME | REQUEST, MT_RESUME, bc?bc->l3_id:-1, sizeof(RESUME_t) ,nt);
00908
00909 #ifdef DEBUG
00910 printf("Building RESUME Msg\n");
00911 #endif
00912 return msg;
00913 }
00914
00915 static void parse_hold_acknowledge (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00916 {
00917 #ifdef DEBUG
00918 printf("Parsing HOLD_ACKNOWLEDGE Msg\n");
00919 #endif
00920
00921
00922 }
00923
00924 static msg_t *build_hold_acknowledge (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00925 {
00926 msg_t *msg =(msg_t*)create_l3msg(CC_HOLD_ACKNOWLEDGE | REQUEST, MT_HOLD_ACKNOWLEDGE, bc?bc->l3_id:-1, sizeof(HOLD_ACKNOWLEDGE_t) ,nt);
00927
00928 #ifdef DEBUG
00929 printf("Building HOLD_ACKNOWLEDGE Msg\n");
00930 #endif
00931 return msg;
00932 }
00933
00934 static void parse_suspend_acknowledge (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00935 {
00936 #ifdef DEBUG
00937 printf("Parsing SUSPEND_ACKNOWLEDGE Msg\n");
00938 #endif
00939
00940
00941 }
00942
00943 static msg_t *build_suspend_acknowledge (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00944 {
00945 msg_t *msg =(msg_t*)create_l3msg(CC_SUSPEND_ACKNOWLEDGE | REQUEST, MT_SUSPEND_ACKNOWLEDGE, bc?bc->l3_id:-1, sizeof(SUSPEND_ACKNOWLEDGE_t) ,nt);
00946
00947 #ifdef DEBUG
00948 printf("Building SUSPEND_ACKNOWLEDGE Msg\n");
00949 #endif
00950 return msg;
00951 }
00952
00953 static void parse_resume_acknowledge (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00954 {
00955 #ifdef DEBUG
00956 printf("Parsing RESUME_ACKNOWLEDGE Msg\n");
00957 #endif
00958
00959
00960 }
00961
00962 static msg_t *build_resume_acknowledge (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00963 {
00964 msg_t *msg =(msg_t*)create_l3msg(CC_RESUME_ACKNOWLEDGE | REQUEST, MT_RESUME_ACKNOWLEDGE, bc?bc->l3_id:-1, sizeof(RESUME_ACKNOWLEDGE_t) ,nt);
00965
00966 #ifdef DEBUG
00967 printf("Building RESUME_ACKNOWLEDGE Msg\n");
00968 #endif
00969 return msg;
00970 }
00971
00972 static void parse_hold_reject (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00973 {
00974 #ifdef DEBUG
00975 printf("Parsing HOLD_REJECT Msg\n");
00976 #endif
00977
00978
00979 }
00980
00981 static msg_t *build_hold_reject (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
00982 {
00983 msg_t *msg =(msg_t*)create_l3msg(CC_HOLD_REJECT | REQUEST, MT_HOLD_REJECT, bc?bc->l3_id:-1, sizeof(HOLD_REJECT_t) ,nt);
00984
00985 #ifdef DEBUG
00986 printf("Building HOLD_REJECT Msg\n");
00987 #endif
00988 return msg;
00989 }
00990
00991 static void parse_retrieve (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
00992 {
00993 #ifdef DEBUG
00994 printf("Parsing RETRIEVE Msg\n");
00995 #endif
00996
00997
00998 }
00999
01000 static msg_t *build_retrieve (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01001 {
01002 msg_t *msg =(msg_t*)create_l3msg(CC_RETRIEVE | REQUEST, MT_RETRIEVE, bc?bc->l3_id:-1, sizeof(RETRIEVE_t) ,nt);
01003
01004 #ifdef DEBUG
01005 printf("Building RETRIEVE Msg\n");
01006 #endif
01007 return msg;
01008 }
01009
01010 static void parse_retrieve_acknowledge (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01011 {
01012 #ifdef DEBUG
01013 printf("Parsing RETRIEVE_ACKNOWLEDGE Msg\n");
01014 #endif
01015
01016
01017 }
01018
01019 static msg_t *build_retrieve_acknowledge (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01020 {
01021 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01022 RETRIEVE_ACKNOWLEDGE_t *retrieve_acknowledge;
01023 msg_t *msg =(msg_t*)create_l3msg(CC_RETRIEVE_ACKNOWLEDGE | REQUEST, MT_RETRIEVE_ACKNOWLEDGE, bc?bc->l3_id:-1, sizeof(RETRIEVE_ACKNOWLEDGE_t) ,nt);
01024
01025 retrieve_acknowledge=(RETRIEVE_ACKNOWLEDGE_t*)((msg->data+HEADER_LEN));
01026
01027 enc_ie_channel_id(&retrieve_acknowledge->CHANNEL_ID, msg, 1, bc->channel, nt,bc);
01028 #ifdef DEBUG
01029 printf("Building RETRIEVE_ACKNOWLEDGE Msg\n");
01030 #endif
01031 return msg;
01032 }
01033
01034 static void parse_retrieve_reject (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01035 {
01036 #ifdef DEBUG
01037 printf("Parsing RETRIEVE_REJECT Msg\n");
01038 #endif
01039
01040
01041 }
01042
01043 static msg_t *build_retrieve_reject (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01044 {
01045 msg_t *msg =(msg_t*)create_l3msg(CC_RETRIEVE_REJECT | REQUEST, MT_RETRIEVE_REJECT, bc?bc->l3_id:-1, sizeof(RETRIEVE_REJECT_t) ,nt);
01046
01047 #ifdef DEBUG
01048 printf("Building RETRIEVE_REJECT Msg\n");
01049 #endif
01050 return msg;
01051 }
01052
01053 static void parse_disconnect (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01054 {
01055 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01056 DISCONNECT_t *disconnect = (DISCONNECT_t *) (msg->data + HEADER_LEN);
01057 int location;
01058 int cause;
01059 dec_ie_cause(disconnect->CAUSE, (Q931_info_t *)(disconnect), &location, &cause, nt,bc);
01060 if (cause>0) bc->cause=cause;
01061
01062 dec_ie_facility(disconnect->FACILITY, (Q931_info_t *) disconnect, &bc->fac_in, nt, bc);
01063
01064 dec_ie_progress(disconnect->PROGRESS, (Q931_info_t *)disconnect, &bc->progress_coding, &bc->progress_location, &bc->progress_indicator, nt, bc);
01065 #ifdef DEBUG
01066 printf("Parsing DISCONNECT Msg\n");
01067 #endif
01068
01069
01070 }
01071
01072 static msg_t *build_disconnect (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01073 {
01074 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01075 DISCONNECT_t *disconnect;
01076 msg_t *msg =(msg_t*)create_l3msg(CC_DISCONNECT | REQUEST, MT_DISCONNECT, bc?bc->l3_id:-1, sizeof(DISCONNECT_t) ,nt);
01077
01078 disconnect=(DISCONNECT_t*)((msg->data+HEADER_LEN));
01079
01080 enc_ie_cause(&disconnect->CAUSE, msg, (nt)?1:0, bc->out_cause,nt,bc);
01081 if (nt) {
01082 enc_ie_progress(&disconnect->PROGRESS, msg, 0, nt ? 1 : 5, 8, nt, bc);
01083 }
01084
01085 if (bc->fac_out.Function != Fac_None) {
01086 enc_ie_facility(&disconnect->FACILITY, msg, &bc->fac_out, nt);
01087 }
01088
01089 if (bc->uulen) {
01090 int protocol=4;
01091 enc_ie_useruser(&disconnect->USER_USER, msg, protocol, bc->uu, bc->uulen, nt,bc);
01092 cb_log(1, bc->port, "ENCODING USERUSERINFO:%s\n", bc->uu);
01093 }
01094
01095 #ifdef DEBUG
01096 printf("Building DISCONNECT Msg\n");
01097 #endif
01098 return msg;
01099 }
01100
01101 static void parse_restart (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01102 {
01103 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01104 RESTART_t *restart = (RESTART_t *) (msg->data + HEADER_LEN);
01105
01106 struct misdn_stack *stack=get_stack_by_bc(bc);
01107
01108 #ifdef DEBUG
01109 printf("Parsing RESTART Msg\n");
01110 #endif
01111
01112 {
01113 int exclusive;
01114 dec_ie_channel_id(restart->CHANNEL_ID, (Q931_info_t *)restart, &exclusive, &bc->restart_channel, nt,bc);
01115 cb_log(3, stack->port, "CC_RESTART Request on channel:%d on this port.\n", bc->restart_channel);
01116 }
01117
01118 }
01119
01120 static msg_t *build_restart (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01121 {
01122 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01123 RESTART_t *restart;
01124 msg_t *msg =(msg_t*)create_l3msg(CC_RESTART | REQUEST, MT_RESTART, bc?bc->l3_id:-1, sizeof(RESTART_t) ,nt);
01125
01126 restart=(RESTART_t*)((msg->data+HEADER_LEN));
01127
01128 #ifdef DEBUG
01129 printf("Building RESTART Msg\n");
01130 #endif
01131
01132 if (bc->channel > 0) {
01133 enc_ie_channel_id(&restart->CHANNEL_ID, msg, 1,bc->channel, nt,bc);
01134 enc_ie_restart_ind(&restart->RESTART_IND, msg, 0x80, nt, bc);
01135 } else {
01136 enc_ie_restart_ind(&restart->RESTART_IND, msg, 0x87, nt, bc);
01137 }
01138
01139 cb_log(0,bc->port, "Restarting channel %d\n", bc->channel);
01140 return msg;
01141 }
01142
01143 static void parse_release (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01144 {
01145 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01146 RELEASE_t *release = (RELEASE_t *) (msg->data + HEADER_LEN);
01147 int location;
01148 int cause;
01149
01150 dec_ie_cause(release->CAUSE, (Q931_info_t *)(release), &location, &cause, nt,bc);
01151 if (cause>0) bc->cause=cause;
01152
01153 dec_ie_facility(release->FACILITY, (Q931_info_t *) release, &bc->fac_in, nt, bc);
01154
01155 #ifdef DEBUG
01156 printf("Parsing RELEASE Msg\n");
01157 #endif
01158
01159
01160 }
01161
01162 static msg_t *build_release (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01163 {
01164 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01165 RELEASE_t *release;
01166 msg_t *msg =(msg_t*)create_l3msg(CC_RELEASE | REQUEST, MT_RELEASE, bc?bc->l3_id:-1, sizeof(RELEASE_t) ,nt);
01167
01168 release=(RELEASE_t*)((msg->data+HEADER_LEN));
01169
01170 if (bc->out_cause>= 0)
01171 enc_ie_cause(&release->CAUSE, msg, nt?1:0, bc->out_cause, nt,bc);
01172
01173 if (bc->fac_out.Function != Fac_None) {
01174 enc_ie_facility(&release->FACILITY, msg, &bc->fac_out, nt);
01175 }
01176
01177 if (bc->uulen) {
01178 int protocol=4;
01179 enc_ie_useruser(&release->USER_USER, msg, protocol, bc->uu, bc->uulen, nt,bc);
01180 cb_log(1, bc->port, "ENCODING USERUSERINFO:%s\n", bc->uu);
01181 }
01182
01183 #ifdef DEBUG
01184 printf("Building RELEASE Msg\n");
01185 #endif
01186 return msg;
01187 }
01188
01189 static void parse_release_complete (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01190 {
01191 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01192 RELEASE_COMPLETE_t *release_complete = (RELEASE_COMPLETE_t *) (msg->data + HEADER_LEN);
01193 int location;
01194 int cause;
01195 iframe_t *frm = (iframe_t*) msg->data;
01196
01197 struct misdn_stack *stack=get_stack_by_bc(bc);
01198 mISDNuser_head_t *hh;
01199 hh=(mISDNuser_head_t*)msg->data;
01200
01201
01202
01203
01204 if (nt) {
01205 if (hh->prim == (CC_RELEASE_COMPLETE|CONFIRM)) {
01206 cb_log(0, stack->port, "CC_RELEASE_COMPLETE|CONFIRM [NT] \n");
01207 return;
01208 }
01209 } else {
01210 if (frm->prim == (CC_RELEASE_COMPLETE|CONFIRM)) {
01211 cb_log(0, stack->port, "CC_RELEASE_COMPLETE|CONFIRM [TE] \n");
01212 return;
01213 }
01214 }
01215 dec_ie_cause(release_complete->CAUSE, (Q931_info_t *)(release_complete), &location, &cause, nt,bc);
01216 if (cause>0) bc->cause=cause;
01217
01218 dec_ie_facility(release_complete->FACILITY, (Q931_info_t *) release_complete, &bc->fac_in, nt, bc);
01219
01220 #ifdef DEBUG
01221 printf("Parsing RELEASE_COMPLETE Msg\n");
01222 #endif
01223 }
01224
01225 static msg_t *build_release_complete (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01226 {
01227 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01228 RELEASE_COMPLETE_t *release_complete;
01229 msg_t *msg =(msg_t*)create_l3msg(CC_RELEASE_COMPLETE | REQUEST, MT_RELEASE_COMPLETE, bc?bc->l3_id:-1, sizeof(RELEASE_COMPLETE_t) ,nt);
01230
01231 release_complete=(RELEASE_COMPLETE_t*)((msg->data+HEADER_LEN));
01232
01233 enc_ie_cause(&release_complete->CAUSE, msg, nt?1:0, bc->out_cause, nt,bc);
01234
01235 if (bc->fac_out.Function != Fac_None) {
01236 enc_ie_facility(&release_complete->FACILITY, msg, &bc->fac_out, nt);
01237 }
01238
01239 if (bc->uulen) {
01240 int protocol=4;
01241 enc_ie_useruser(&release_complete->USER_USER, msg, protocol, bc->uu, bc->uulen, nt,bc);
01242 cb_log(1, bc->port, "ENCODING USERUSERINFO:%s\n", bc->uu);
01243 }
01244
01245 #ifdef DEBUG
01246 printf("Building RELEASE_COMPLETE Msg\n");
01247 #endif
01248 return msg;
01249 }
01250
01251 static void parse_facility (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01252 {
01253 int HEADER_LEN = nt ? mISDNUSER_HEAD_SIZE : mISDN_HEADER_LEN;
01254 FACILITY_t *facility = (FACILITY_t*)(msg->data+HEADER_LEN);
01255 Q931_info_t *qi = (Q931_info_t*)(msg->data+HEADER_LEN);
01256 unsigned char *p = NULL;
01257 #if defined(AST_MISDN_ENHANCEMENTS)
01258 int description_code;
01259 int type;
01260 int plan;
01261 int present;
01262 char number[sizeof(bc->redirecting.to.number)];
01263 #endif
01264
01265 #ifdef DEBUG
01266 printf("Parsing FACILITY Msg\n");
01267 #endif
01268
01269 bc->fac_in.Function = Fac_None;
01270
01271 if (!bc->nt) {
01272 if (qi->QI_ELEMENT(facility))
01273 p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(facility) + 1;
01274 } else {
01275 p = facility->FACILITY;
01276 }
01277 if (!p)
01278 return;
01279
01280 if (decodeFac(p, &bc->fac_in)) {
01281 cb_log(3, bc->port, "Decoding facility ie failed! Unrecognized facility message?\n");
01282 }
01283
01284 #if defined(AST_MISDN_ENHANCEMENTS)
01285 dec_ie_notify(facility->NOTIFY, qi, &description_code, nt, bc);
01286 if (description_code < 0) {
01287 bc->notify_description_code = mISDN_NOTIFY_CODE_INVALID;
01288 } else {
01289 bc->notify_description_code = description_code;
01290 }
01291
01292 dec_ie_redir_dn(facility->REDIR_DN, qi, &type, &plan, &present, number, sizeof(number), nt, bc);
01293 if (0 <= type) {
01294 bc->redirecting.to_changed = 1;
01295
01296 bc->redirecting.to.number_type = type;
01297 bc->redirecting.to.number_plan = plan;
01298 switch (present) {
01299 default:
01300 case 0:
01301 bc->redirecting.to.presentation = 0;
01302 break;
01303 case 1:
01304 bc->redirecting.to.presentation = 1;
01305 break;
01306 case 2:
01307 bc->redirecting.to.presentation = 2;
01308 break;
01309 }
01310 bc->redirecting.to.screening = 0;
01311 strcpy(bc->redirecting.to.number, number);
01312 }
01313 #endif
01314 }
01315
01316 static msg_t *build_facility (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01317 {
01318 int len;
01319 int HEADER_LEN;
01320 unsigned char *ie_fac;
01321 unsigned char fac_tmp[256];
01322 msg_t *msg;
01323 FACILITY_t *facility;
01324 Q931_info_t *qi;
01325
01326 #ifdef DEBUG
01327 printf("Building FACILITY Msg\n");
01328 #endif
01329
01330 len = encodeFac(fac_tmp, &(bc->fac_out));
01331 if (len <= 0) {
01332
01333
01334
01335
01336 bc->fac_out.Function = Fac_None;
01337
01338 #if defined(AST_MISDN_ENHANCEMENTS)
01339
01340 bc->notify_description_code = mISDN_NOTIFY_CODE_INVALID;
01341 bc->redirecting.to_changed = 0;
01342 #endif
01343 return NULL;
01344 }
01345
01346 msg = (msg_t *) create_l3msg(CC_FACILITY | REQUEST, MT_FACILITY, bc ? bc->l3_id : -1, sizeof(FACILITY_t), nt);
01347 HEADER_LEN = nt ? mISDNUSER_HEAD_SIZE : mISDN_HEADER_LEN;
01348 facility = (FACILITY_t *) (msg->data + HEADER_LEN);
01349
01350 ie_fac = msg_put(msg, len);
01351 if (bc->nt) {
01352 facility->FACILITY = ie_fac + 1;
01353 } else {
01354 qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
01355 qi->QI_ELEMENT(facility) = ie_fac - (unsigned char *)qi - sizeof(Q931_info_t);
01356 }
01357
01358 memcpy(ie_fac, fac_tmp, len);
01359
01360
01361 bc->fac_out.Function = Fac_None;
01362
01363 if (*bc->display) {
01364 #ifdef DEBUG
01365 printf("Sending %s as Display\n", bc->display);
01366 #endif
01367 enc_ie_display(&facility->DISPLAY, msg, bc->display, nt,bc);
01368 }
01369
01370 #if defined(AST_MISDN_ENHANCEMENTS)
01371 if (bc->notify_description_code != mISDN_NOTIFY_CODE_INVALID) {
01372 enc_ie_notify(&facility->NOTIFY, msg, bc->notify_description_code, nt, bc);
01373 bc->notify_description_code = mISDN_NOTIFY_CODE_INVALID;
01374 }
01375
01376 if (bc->redirecting.to_changed) {
01377 bc->redirecting.to_changed = 0;
01378 switch (bc->outgoing_colp) {
01379 case 0:
01380 case 1:
01381 enc_ie_redir_dn(&facility->REDIR_DN, msg, bc->redirecting.to.number_type,
01382 bc->redirecting.to.number_plan, bc->redirecting.to.presentation,
01383 bc->redirecting.to.number, nt, bc);
01384 break;
01385 default:
01386 break;
01387 }
01388 }
01389 #endif
01390
01391 return msg;
01392 }
01393
01394 #if defined(AST_MISDN_ENHANCEMENTS)
01395
01396
01397
01398
01399
01400
01401
01402
01403
01404
01405
01406 static void parse_register(struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01407 {
01408 int HEADER_LEN;
01409 REGISTER_t *reg;
01410
01411 HEADER_LEN = nt ? mISDNUSER_HEAD_SIZE : mISDN_HEADER_LEN;
01412 reg = (REGISTER_t *) (msg->data + HEADER_LEN);
01413
01414
01415
01416
01417
01418
01419 dec_ie_facility(reg->FACILITY, (Q931_info_t *) reg, &bc->fac_in, nt, bc);
01420 }
01421 #endif
01422
01423 #if defined(AST_MISDN_ENHANCEMENTS)
01424
01425
01426
01427
01428
01429
01430
01431
01432
01433
01434 static msg_t *build_register(struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01435 {
01436 int HEADER_LEN;
01437 REGISTER_t *reg;
01438 msg_t *msg;
01439
01440 msg = (msg_t *) create_l3msg(CC_REGISTER | REQUEST, MT_REGISTER, bc ? bc->l3_id : -1, sizeof(REGISTER_t), nt);
01441 HEADER_LEN = nt ? mISDNUSER_HEAD_SIZE : mISDN_HEADER_LEN;
01442 reg = (REGISTER_t *) (msg->data + HEADER_LEN);
01443
01444 if (bc->fac_out.Function != Fac_None) {
01445 enc_ie_facility(®->FACILITY, msg, &bc->fac_out, nt);
01446 }
01447
01448 return msg;
01449 }
01450 #endif
01451
01452 static void parse_notify (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01453 {
01454 int HEADER_LEN = nt ? mISDNUSER_HEAD_SIZE : mISDN_HEADER_LEN;
01455 NOTIFY_t *notify = (NOTIFY_t *) (msg->data + HEADER_LEN);
01456 int description_code;
01457 int type;
01458 int plan;
01459 int present;
01460 char number[sizeof(bc->redirecting.to.number)];
01461
01462 #ifdef DEBUG
01463 printf("Parsing NOTIFY Msg\n");
01464 #endif
01465
01466 dec_ie_notify(notify->NOTIFY, (Q931_info_t *) notify, &description_code, nt, bc);
01467 if (description_code < 0) {
01468 bc->notify_description_code = mISDN_NOTIFY_CODE_INVALID;
01469 } else {
01470 bc->notify_description_code = description_code;
01471 }
01472
01473 dec_ie_redir_dn(notify->REDIR_DN, (Q931_info_t *) notify, &type, &plan, &present, number, sizeof(number), nt, bc);
01474 if (0 <= type) {
01475 bc->redirecting.to_changed = 1;
01476
01477 bc->redirecting.to.number_type = type;
01478 bc->redirecting.to.number_plan = plan;
01479 switch (present) {
01480 default:
01481 case 0:
01482 bc->redirecting.to.presentation = 0;
01483 break;
01484 case 1:
01485 bc->redirecting.to.presentation = 1;
01486 break;
01487 case 2:
01488 bc->redirecting.to.presentation = 2;
01489 break;
01490 }
01491 bc->redirecting.to.screening = 0;
01492 strcpy(bc->redirecting.to.number, number);
01493 }
01494 }
01495
01496 static msg_t *build_notify (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01497 {
01498 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01499 NOTIFY_t *notify;
01500 msg_t *msg =(msg_t*)create_l3msg(CC_NOTIFY | REQUEST, MT_NOTIFY, bc?bc->l3_id:-1, sizeof(NOTIFY_t) ,nt);
01501
01502 #ifdef DEBUG
01503 printf("Building NOTIFY Msg\n");
01504 #endif
01505
01506 notify = (NOTIFY_t *) (msg->data + HEADER_LEN);
01507
01508 enc_ie_notify(¬ify->NOTIFY, msg, bc->notify_description_code, nt, bc);
01509 bc->notify_description_code = mISDN_NOTIFY_CODE_INVALID;
01510
01511 if (bc->redirecting.to_changed) {
01512 bc->redirecting.to_changed = 0;
01513 switch (bc->outgoing_colp) {
01514 case 0:
01515 case 1:
01516 enc_ie_redir_dn(¬ify->REDIR_DN, msg, bc->redirecting.to.number_type,
01517 bc->redirecting.to.number_plan, bc->redirecting.to.presentation,
01518 bc->redirecting.to.number, nt, bc);
01519 break;
01520 default:
01521 break;
01522 }
01523 }
01524 return msg;
01525 }
01526
01527 static void parse_status_enquiry (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01528 {
01529 #ifdef DEBUG
01530 printf("Parsing STATUS_ENQUIRY Msg\n");
01531 #endif
01532 }
01533
01534 static msg_t *build_status_enquiry (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01535 {
01536 msg_t *msg =(msg_t*)create_l3msg(CC_STATUS_ENQUIRY | REQUEST, MT_STATUS_ENQUIRY, bc?bc->l3_id:-1, sizeof(STATUS_ENQUIRY_t) ,nt);
01537
01538 #ifdef DEBUG
01539 printf("Building STATUS_ENQUIRY Msg\n");
01540 #endif
01541 return msg;
01542 }
01543
01544 static void parse_information (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01545 {
01546 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01547 INFORMATION_t *information = (INFORMATION_t *) (msg->data + HEADER_LEN);
01548 int type, plan;
01549
01550 dec_ie_called_pn(information->CALLED_PN, (Q931_info_t *) information, &type, &plan, bc->info_dad, sizeof(bc->info_dad), nt, bc);
01551 dec_ie_keypad(information->KEYPAD, (Q931_info_t *) information, bc->keypad, sizeof(bc->keypad), nt, bc);
01552
01553 #ifdef DEBUG
01554 printf("Parsing INFORMATION Msg\n");
01555 #endif
01556 }
01557
01558 static msg_t *build_information (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01559 {
01560 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01561 INFORMATION_t *information;
01562 msg_t *msg =(msg_t*)create_l3msg(CC_INFORMATION | REQUEST, MT_INFORMATION, bc?bc->l3_id:-1, sizeof(INFORMATION_t) ,nt);
01563
01564 information=(INFORMATION_t*)((msg->data+HEADER_LEN));
01565
01566 enc_ie_called_pn(&information->CALLED_PN, msg, 0, 1, bc->info_dad, nt,bc);
01567
01568 {
01569 if (*bc->display) {
01570 #ifdef DEBUG
01571 printf("Sending %s as Display\n", bc->display);
01572 #endif
01573 enc_ie_display(&information->DISPLAY, msg, bc->display, nt,bc);
01574 }
01575 }
01576
01577 #ifdef DEBUG
01578 printf("Building INFORMATION Msg\n");
01579 #endif
01580 return msg;
01581 }
01582
01583 static void parse_status (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01584 {
01585 int HEADER_LEN = nt?mISDNUSER_HEAD_SIZE:mISDN_HEADER_LEN;
01586 STATUS_t *status = (STATUS_t *) (msg->data + HEADER_LEN);
01587 int location;
01588 int cause;
01589
01590 dec_ie_cause(status->CAUSE, (Q931_info_t *)(status), &location, &cause, nt,bc);
01591 if (cause>0) bc->cause=cause;
01592
01593 #ifdef DEBUG
01594 printf("Parsing STATUS Msg\n");
01595 #endif
01596 }
01597
01598 static msg_t *build_status (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01599 {
01600 msg_t *msg =(msg_t*)create_l3msg(CC_STATUS | REQUEST, MT_STATUS, bc?bc->l3_id:-1, sizeof(STATUS_t) ,nt);
01601
01602 #ifdef DEBUG
01603 printf("Building STATUS Msg\n");
01604 #endif
01605 return msg;
01606 }
01607
01608 static void parse_timeout (struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01609 {
01610 #ifdef DEBUG
01611 printf("Parsing STATUS Msg\n");
01612 #endif
01613 }
01614
01615 static msg_t *build_timeout (struct isdn_msg msgs[], struct misdn_bchannel *bc, int nt)
01616 {
01617 msg_t *msg =(msg_t*)create_l3msg(CC_STATUS | REQUEST, MT_STATUS, bc?bc->l3_id:-1, sizeof(STATUS_t) ,nt);
01618
01619 #ifdef DEBUG
01620 printf("Building STATUS Msg\n");
01621 #endif
01622 return msg;
01623 }
01624
01625
01626
01627
01628
01629
01630
01631
01632
01633 struct isdn_msg msgs_g[] = {
01634
01635
01636 { CC_PROCEEDING, EVENT_PROCEEDING, parse_proceeding, build_proceeding, "PROCEEDING" },
01637 { CC_ALERTING, EVENT_ALERTING, parse_alerting, build_alerting, "ALERTING" },
01638 { CC_PROGRESS, EVENT_PROGRESS, parse_progress, build_progress, "PROGRESS" },
01639 { CC_SETUP, EVENT_SETUP, parse_setup, build_setup, "SETUP" },
01640 #if defined(AST_MISDN_ENHANCEMENTS)
01641 { CC_REGISTER, EVENT_REGISTER, parse_register, build_register, "REGISTER" },
01642 #endif
01643 { CC_CONNECT, EVENT_CONNECT, parse_connect, build_connect, "CONNECT" },
01644 { CC_SETUP_ACKNOWLEDGE, EVENT_SETUP_ACKNOWLEDGE, parse_setup_acknowledge, build_setup_acknowledge, "SETUP_ACKNOWLEDGE" },
01645 { CC_CONNECT_ACKNOWLEDGE, EVENT_CONNECT_ACKNOWLEDGE, parse_connect_acknowledge, build_connect_acknowledge, "CONNECT_ACKNOWLEDGE " },
01646 { CC_USER_INFORMATION, EVENT_USER_INFORMATION, parse_user_information, build_user_information, "USER_INFORMATION" },
01647 { CC_SUSPEND_REJECT, EVENT_SUSPEND_REJECT, parse_suspend_reject, build_suspend_reject, "SUSPEND_REJECT" },
01648 { CC_RESUME_REJECT, EVENT_RESUME_REJECT, parse_resume_reject, build_resume_reject, "RESUME_REJECT" },
01649 { CC_HOLD, EVENT_HOLD, parse_hold, build_hold, "HOLD" },
01650 { CC_SUSPEND, EVENT_SUSPEND, parse_suspend, build_suspend, "SUSPEND" },
01651 { CC_RESUME, EVENT_RESUME, parse_resume, build_resume, "RESUME" },
01652 { CC_HOLD_ACKNOWLEDGE, EVENT_HOLD_ACKNOWLEDGE, parse_hold_acknowledge, build_hold_acknowledge, "HOLD_ACKNOWLEDGE" },
01653 { CC_SUSPEND_ACKNOWLEDGE, EVENT_SUSPEND_ACKNOWLEDGE, parse_suspend_acknowledge, build_suspend_acknowledge, "SUSPEND_ACKNOWLEDGE" },
01654 { CC_RESUME_ACKNOWLEDGE, EVENT_RESUME_ACKNOWLEDGE, parse_resume_acknowledge, build_resume_acknowledge, "RESUME_ACKNOWLEDGE" },
01655 { CC_HOLD_REJECT, EVENT_HOLD_REJECT, parse_hold_reject, build_hold_reject, "HOLD_REJECT" },
01656 { CC_RETRIEVE, EVENT_RETRIEVE, parse_retrieve, build_retrieve, "RETRIEVE" },
01657 { CC_RETRIEVE_ACKNOWLEDGE, EVENT_RETRIEVE_ACKNOWLEDGE, parse_retrieve_acknowledge, build_retrieve_acknowledge, "RETRIEVE_ACKNOWLEDGE" },
01658 { CC_RETRIEVE_REJECT, EVENT_RETRIEVE_REJECT, parse_retrieve_reject, build_retrieve_reject, "RETRIEVE_REJECT" },
01659 { CC_DISCONNECT, EVENT_DISCONNECT, parse_disconnect, build_disconnect, "DISCONNECT" },
01660 { CC_RESTART, EVENT_RESTART, parse_restart, build_restart, "RESTART" },
01661 { CC_RELEASE, EVENT_RELEASE, parse_release, build_release, "RELEASE" },
01662 { CC_RELEASE_COMPLETE, EVENT_RELEASE_COMPLETE, parse_release_complete, build_release_complete, "RELEASE_COMPLETE" },
01663 { CC_FACILITY, EVENT_FACILITY, parse_facility, build_facility, "FACILITY" },
01664 { CC_NOTIFY, EVENT_NOTIFY, parse_notify, build_notify, "NOTIFY" },
01665 { CC_STATUS_ENQUIRY, EVENT_STATUS_ENQUIRY, parse_status_enquiry, build_status_enquiry, "STATUS_ENQUIRY" },
01666 { CC_INFORMATION, EVENT_INFORMATION, parse_information, build_information, "INFORMATION" },
01667 { CC_STATUS, EVENT_STATUS, parse_status, build_status, "STATUS" },
01668 { CC_TIMEOUT, EVENT_TIMEOUT, parse_timeout, build_timeout, "TIMEOUT" },
01669 { 0, 0, NULL, NULL, NULL }
01670
01671 };
01672
01673 #define msgs_max (sizeof(msgs_g)/sizeof(struct isdn_msg))
01674
01675
01676 int isdn_msg_get_index(struct isdn_msg msgs[], msg_t *msg, int nt)
01677 {
01678 int i;
01679
01680 if (nt){
01681 mISDNuser_head_t *hh = (mISDNuser_head_t*)msg->data;
01682
01683 for (i=0; i< msgs_max -1; i++) {
01684 if ( (hh->prim&COMMAND_MASK)==(msgs[i].misdn_msg&COMMAND_MASK)) return i;
01685 }
01686
01687 } else {
01688 iframe_t *frm = (iframe_t*)msg->data;
01689
01690 for (i=0; i< msgs_max -1; i++)
01691 if ( (frm->prim&COMMAND_MASK)==(msgs[i].misdn_msg&COMMAND_MASK)) return i;
01692 }
01693
01694 return -1;
01695 }
01696
01697 int isdn_msg_get_index_by_event(struct isdn_msg msgs[], enum event_e event, int nt)
01698 {
01699 int i;
01700 for (i=0; i< msgs_max; i++)
01701 if ( event == msgs[i].event) return i;
01702
01703 cb_log(10,0, "get_index: event not found!\n");
01704
01705 return -1;
01706 }
01707
01708 enum event_e isdn_msg_get_event(struct isdn_msg msgs[], msg_t *msg, int nt)
01709 {
01710 int i=isdn_msg_get_index(msgs, msg, nt);
01711 if(i>=0) return msgs[i].event;
01712 return EVENT_UNKNOWN;
01713 }
01714
01715 char * isdn_msg_get_info(struct isdn_msg msgs[], msg_t *msg, int nt)
01716 {
01717 int i=isdn_msg_get_index(msgs, msg, nt);
01718 if(i>=0) return msgs[i].info;
01719 return NULL;
01720 }
01721
01722
01723 char EVENT_CLEAN_INFO[] = "CLEAN_UP";
01724 char EVENT_DTMF_TONE_INFO[] = "DTMF_TONE";
01725 char EVENT_NEW_L3ID_INFO[] = "NEW_L3ID";
01726 char EVENT_NEW_BC_INFO[] = "NEW_BC";
01727 char EVENT_PORT_ALARM_INFO[] = "ALARM";
01728 char EVENT_NEW_CHANNEL_INFO[] = "NEW_CHANNEL";
01729 char EVENT_BCHAN_DATA_INFO[] = "BCHAN_DATA";
01730 char EVENT_BCHAN_ACTIVATED_INFO[] = "BCHAN_ACTIVATED";
01731 char EVENT_TONE_GENERATE_INFO[] = "TONE_GENERATE";
01732 char EVENT_BCHAN_ERROR_INFO[] = "BCHAN_ERROR";
01733
01734 char * isdn_get_info(struct isdn_msg msgs[], enum event_e event, int nt)
01735 {
01736 int i=isdn_msg_get_index_by_event(msgs, event, nt);
01737
01738 if(i>=0) return msgs[i].info;
01739
01740 if (event == EVENT_CLEANUP) return EVENT_CLEAN_INFO;
01741 if (event == EVENT_DTMF_TONE) return EVENT_DTMF_TONE_INFO;
01742 if (event == EVENT_NEW_L3ID) return EVENT_NEW_L3ID_INFO;
01743 if (event == EVENT_NEW_BC) return EVENT_NEW_BC_INFO;
01744 if (event == EVENT_NEW_CHANNEL) return EVENT_NEW_CHANNEL_INFO;
01745 if (event == EVENT_BCHAN_DATA) return EVENT_BCHAN_DATA_INFO;
01746 if (event == EVENT_BCHAN_ACTIVATED) return EVENT_BCHAN_ACTIVATED_INFO;
01747 if (event == EVENT_TONE_GENERATE) return EVENT_TONE_GENERATE_INFO;
01748 if (event == EVENT_PORT_ALARM) return EVENT_PORT_ALARM_INFO;
01749 if (event == EVENT_BCHAN_ERROR) return EVENT_BCHAN_ERROR_INFO;
01750
01751 return NULL;
01752 }
01753
01754 int isdn_msg_parse_event(struct isdn_msg msgs[], msg_t *msg, struct misdn_bchannel *bc, int nt)
01755 {
01756 int i=isdn_msg_get_index(msgs, msg, nt);
01757 if(i<0) return -1;
01758
01759 msgs[i].msg_parser(msgs, msg, bc, nt);
01760 return 0;
01761 }
01762
01763 msg_t * isdn_msg_build_event(struct isdn_msg msgs[], struct misdn_bchannel *bc, enum event_e event, int nt)
01764 {
01765 int i=isdn_msg_get_index_by_event(msgs, event, nt);
01766 if(i<0) return NULL;
01767
01768 return msgs[i].msg_builder(msgs, bc, nt);
01769 }