From: Super User Date: Sat, 11 Aug 2007 08:12:10 +0000 (+0200) Subject: fixes, debugging for usleep problems. X-Git-Url: http://git.eversberg.eu/gitweb.cgi?p=lcr.git;a=commitdiff_plain;h=0a0643e3a561de5f34927ea80c2bd0ce6405fd3c fixes, debugging for usleep problems. --- diff --git a/apppbx.cpp b/apppbx.cpp index 61458e7..1cef961 100644 --- a/apppbx.cpp +++ b/apppbx.cpp @@ -1614,7 +1614,6 @@ void EndpointAppPBX::port_setup(struct port_list *portlist, int message_type, un memcpy(&e_redirinfo, ¶m->setup.redirinfo, sizeof(e_redirinfo)); memcpy(&e_capainfo, ¶m->setup.capainfo, sizeof(e_capainfo)); e_dtmf = param->setup.dtmf; - /* screen incoming caller id */ interface = interface_first; while(interface) @@ -1774,7 +1773,8 @@ void EndpointAppPBX::port_information(struct port_list *portlist, int message_ty /* turn off dtmf detection, in case dtmf is sent with keypad information */ if (e_dtmf) { - PDEBUG(DEBUG_EPOINT, "EPOINT(%d) received dialing information, so dtmf is now disabled, to prevent double detection by keypad+dtmf.\n", ea_endpoint->ep_serial, param->information.id, e_ext.number, e_callerinfo.id); + trace_header("DTMF (disabling due to keypad)", DIRECTION_IN); + end_trace(); e_dtmf = 0; } @@ -1801,21 +1801,29 @@ void EndpointAppPBX::port_information(struct port_list *portlist, int message_ty } /* keypad when connected */ - if (e_state == EPOINT_STATE_CONNECT && e_ext.keypad) + if (e_state == EPOINT_STATE_CONNECT) { - PDEBUG(DEBUG_EPOINT, "EPOINT(%d) keypad information received during connect: %s.\n", ea_endpoint->ep_serial, param->information.id); - /* processing keypad function */ - if (param->information.id[0] == '0') + if (e_ext.keypad) { - hookflash(); + PDEBUG(DEBUG_EPOINT, "EPOINT(%d) keypad information received during connect: %s.\n", ea_endpoint->ep_serial, param->information.id); + /* processing keypad function */ + if (param->information.id[0] == '0') + { + hookflash(); + } + if (param->information.id[0]) + keypad_function(param->information.id[0]); + } else + { + trace_header("DTMF (not enabled by extension's settings)", DIRECTION_IN); + end_trace(); } - if (param->information.id[0]) - keypad_function(param->information.id[0]); return; } if (e_state != EPOINT_STATE_IN_OVERLAP) { - PDEBUG(DEBUG_EPOINT, "EPOINT(%d) ignored because we are not in overlap, or connect state.\n", ea_endpoint->ep_serial); + trace_header("DTMF (ignored, not connected and not dialing)", DIRECTION_IN); + end_trace(); return; } if (!param->information.id[0]) @@ -1841,15 +1849,16 @@ void EndpointAppPBX::port_information(struct port_list *portlist, int message_ty /* port MESSAGE_DTMF */ void EndpointAppPBX::port_dtmf(struct port_list *portlist, int message_type, union parameter *param) { - trace_header("DTMF", DIRECTION_IN); - add_trace("digit", NULL, "%c", param->dtmf); - end_trace(); /* only if dtmf detection is enabled */ if (!e_dtmf) { - PDEBUG(DEBUG_EPOINT, "dtmf detection is disabled\n"); + trace_header("DTMF (disabled)", DIRECTION_IN); + end_trace(); return; } + trace_header("DTMF", DIRECTION_IN); + add_trace("digit", NULL, "%c", param->dtmf); + end_trace(); #if 0 NOTE: vbox is now handled due to overlap state @@ -2892,6 +2901,16 @@ void EndpointAppPBX::ea_message_port(unsigned long port_id, int message_type, un port_resume(portlist, message_type, param); break; + /* port assigns bchannel */ + case MESSAGE_BCHANNEL: /* indicates the assigned bchannel */ + case MESSAGE_BCHANNEL_FREE: /* requests bchannel back (e.g. when call is holded) */ + PDEBUG(DEBUG_EPOINT, "EPOINT(%d) epoint with terminal '%s' (caller id '%s') received bchannel assignment.\n", ea_endpoint->ep_serial, e_ext.number, e_callerinfo.id); + /* only one port is expected to be connected to bchannel */ + message = message_forward(ea_endpoint->ep_serial, ea_endpoint->ep_join_id, EPOINT_TO_JOIN, param); + logmessage(message->type, &message->param, portlist->port_id, DIRECTION_IN); + break; + + default: PDEBUG(DEBUG_EPOINT, "EPOINT(%d) epoint with terminal '%s' (caller id '%s') received a wrong message: %d\n", ea_endpoint->ep_serial, e_ext.number, e_callerinfo.id, message); } @@ -3124,10 +3143,11 @@ void EndpointAppPBX::join_connect(struct port_list *portlist, int message_type, } /* join MESSAGE_DISCONNECT MESSAGE_RELEASE */ -void EndpointAppPBX::join_disconnect_release(struct port_list *portlist, int message_type, union parameter *param) +void EndpointAppPBX::join_disconnect_release(int message_type, union parameter *param) { char cause[16]; struct message *message; + struct port_list *portlist = NULL; /* be sure that we are active */ @@ -3154,11 +3174,11 @@ void EndpointAppPBX::join_disconnect_release(struct port_list *portlist, int mes if (e_state==EPOINT_STATE_IN_OVERLAP) { new_state(EPOINT_STATE_IN_PROCEEDING); - if (portlist) + if (ea_endpoint->ep_portlist) { - message = message_create(ea_endpoint->ep_serial, portlist->port_id, EPOINT_TO_PORT, MESSAGE_PROCEEDING); + message = message_create(ea_endpoint->ep_serial, ea_endpoint->ep_portlist->port_id, EPOINT_TO_PORT, MESSAGE_PROCEEDING); message_put(message); - logmessage(message->type, &message->param, portlist->port_id, DIRECTION_OUT); + logmessage(message->type, &message->param, ea_endpoint->ep_portlist->port_id, DIRECTION_OUT); } /* caused the error, that the first knock sound was not there */ /* set_tone(portlist, "proceeding"); */ @@ -3166,6 +3186,7 @@ void EndpointAppPBX::join_disconnect_release(struct port_list *portlist, int mes /* send display of powerdialing */ if (e_ext.display_dialing) { + portlist = ea_endpoint->ep_portlist; while (portlist) { message = message_create(ea_endpoint->ep_serial, portlist->port_id, EPOINT_TO_PORT, MESSAGE_NOTIFY); @@ -3227,6 +3248,7 @@ void EndpointAppPBX::join_disconnect_release(struct port_list *portlist, int mes } /* send disconnect message */ SCPY(e_tone, cause); + portlist = ea_endpoint->ep_portlist; while(portlist) { set_tone(portlist, cause); @@ -3542,14 +3564,13 @@ void EndpointAppPBX::ea_message_join(unsigned long join_id, int message_type, un case MESSAGE_DISCONNECT: /* call disconnect */ case MESSAGE_RELEASE: /* call releases */ PDEBUG(DEBUG_EPOINT, "EPOINT(%d) epoint with terminal '%s' (caller id '%s') received %s with cause %d location %d\n", ea_endpoint->ep_serial, e_ext.number, e_callerinfo.id, (message_type==MESSAGE_DISCONNECT)?"disconnect":"release", param->disconnectinfo.cause, param->disconnectinfo.location); - join_disconnect_release(portlist, message_type, param); + join_disconnect_release(message_type, param); break; /* CALL sends SETUP message */ case MESSAGE_SETUP: PDEBUG(DEBUG_EPOINT, "EPOINT(%d) epoint received setup from terminal='%s',id='%s' to id='%s' (dialing itype=%d)\n", ea_endpoint->ep_serial, param->setup.callerinfo.extension, param->setup.callerinfo.id, param->setup.dialinginfo.id, param->setup.dialinginfo.itype); join_setup(portlist, message_type, param); - return; break; /* CALL sends special mISDNSIGNAL message */ @@ -3558,6 +3579,22 @@ void EndpointAppPBX::ea_message_join(unsigned long join_id, int message_type, un join_mISDNsignal(portlist, message_type, param); break; + /* call requests bchannel */ + case MESSAGE_BCHANNEL: /* indicates the need of own bchannel access */ + case MESSAGE_BCHANNEL_FREE: /* indicates that the bchannel is free */ + PDEBUG(DEBUG_EPOINT, "EPOINT(%d) epoint with terminal '%s' (caller id '%s') received bchannel request.\n", ea_endpoint->ep_serial, e_ext.number, e_callerinfo.id); + /* only one port is expected to be connected to bchannel */ + if (!portlist) + break; + if (portlist->next) + break; + e_join_pattern = 1; + SCPY(e_tone, ""); + set_tone(portlist, NULL); + message = message_forward(ea_endpoint->ep_serial, portlist->port_id, EPOINT_TO_PORT, param); + logmessage(message->type, &message->param, portlist->port_id, DIRECTION_OUT); + break; + /* CALL has pattern available */ case MESSAGE_PATTERN: /* indicating pattern available */ PDEBUG(DEBUG_EPOINT, "EPOINT(%d) epoint with terminal '%s' (caller id '%s') received pattern availability.\n", ea_endpoint->ep_serial, e_ext.number, e_callerinfo.id); @@ -4441,6 +4478,14 @@ void EndpointAppPBX::logmessage(int message_type, union parameter *param, unsign end_trace(); break; + case MESSAGE_BCHANNEL: + case MESSAGE_BCHANNEL_FREE: + trace_header("BCHANNEL", dir); + if (param->bchannel.addr) + add_trace("address", NULL, "%x", param->bchannel.addr); + end_trace(); + break; + default: PERROR("EPOINT(%d) message not of correct type (%d)\n", ea_endpoint->ep_serial, message_type); } diff --git a/apppbx.h b/apppbx.h index 43404f9..8d5c52c 100644 --- a/apppbx.h +++ b/apppbx.h @@ -214,7 +214,7 @@ class EndpointAppPBX : public EndpointApp void join_proceeding(struct port_list *portlist, int message_type, union parameter *param); void join_alerting(struct port_list *portlist, int message_type, union parameter *param); void join_connect(struct port_list *portlist, int message_type, union parameter *param); - void join_disconnect_release(struct port_list *portlist, int message_type, union parameter *param); + void join_disconnect_release(int message_type, union parameter *param); void join_notify(struct port_list *portlist, int message_type, union parameter *param); void join_facility(struct port_list *portlist, int message_type, union parameter *param); diff --git a/default/interface.conf b/default/interface.conf index 07bc818..04017ae 100644 --- a/default/interface.conf +++ b/default/interface.conf @@ -94,7 +94,7 @@ port 1 [Int] extension -msn 201,202,203 +msn 200,201,202,203 port 2 diff --git a/default/options.conf b/default/options.conf index 21c8697..6c84d97 100644 --- a/default/options.conf +++ b/default/options.conf @@ -31,7 +31,7 @@ # The LCR should run as real time process. Because audio is streamed and # ISDN protocol requires a certain response time, we must have high priority. -# By default, the process runs with realtime scheduling and high priority. +# By default, the process runs an normal priority, lika most processes do. # To debug, it is whise to use "schedule" with no parameter to turn off # realtime scheduling. In case of an endless loop bug, LCR will take # all CPU time forever - your machine hangs. diff --git a/dss1.cpp b/dss1.cpp index 87f49cd..a52f66e 100644 --- a/dss1.cpp +++ b/dss1.cpp @@ -746,6 +746,7 @@ void Pdss1::setup_ind(unsigned long prim, unsigned long dinfo, void *data) message = message_create(p_serial, ACTIVE_EPOINT(p_epointlist), PORT_TO_EPOINT, MESSAGE_SETUP); message->param.setup.isdn_port = p_m_portnum; message->param.setup.port_type = p_type; + message->param.setup.dtmf = !p_m_mISDNport->ifport->nodtmf; memcpy(&message->param.setup.dialinginfo, &p_dialinginfo, sizeof(struct dialing_info)); memcpy(&message->param.setup.callerinfo, &p_callerinfo, sizeof(struct caller_info)); memcpy(&message->param.setup.redirinfo, &p_redirinfo, sizeof(struct redir_info)); @@ -3139,6 +3140,9 @@ int stack2manager_nt(void *dat, void *arg) time(&mISDNport->l2establish); PDEBUG(DEBUG_ISDN, "because we are ptp, we set a l2establish timer.\n"); } +#warning debugging usleep crash + printf("JOLLY release port %d\n", mISDNport->portnum); + usleep(1); break; case CC_SETUP | INDICATION: diff --git a/ie.cpp b/ie.cpp index 75b86f4..f866349 100644 --- a/ie.cpp +++ b/ie.cpp @@ -734,7 +734,17 @@ void Pdss1::enc_ie_channel_id(unsigned char **ntmode, msg_t *msg, int exclusive, } add_trace("channel_id", "exclusive", "%d", exclusive); - add_trace("channel_id", "channel", "%d", channel); + switch(channel) + { + case CHANNEL_ANY: + add_trace("channel_id", "channel", "any channel"); + break; + case CHANNEL_NO: + add_trace("channel_id", "channel", "no channel"); + break; + default: + add_trace("channel_id", "channel", "%d", channel); + } if (!pri) { @@ -874,7 +884,17 @@ void Pdss1::dec_ie_channel_id(unsigned char *p, Q931_info_t *qi, int *exclusive, } add_trace("channel_id", "exclusive", "%d", *exclusive); - add_trace("channel_id", "channel", "%d", *channel); + switch(*channel) + { + case CHANNEL_ANY: + add_trace("channel_id", "channel", "any channel"); + break; + case CHANNEL_NO: + add_trace("channel_id", "channel", "no channel"); + break; + default: + add_trace("channel_id", "channel", "%d", *channel); + } } diff --git a/interface.c b/interface.c index 95973f5..9842e19 100644 --- a/interface.c +++ b/interface.c @@ -678,7 +678,7 @@ struct interface_param interface_param[] = { " any - On outgoing calls, signal 'any channel acceptable'. (see DSS1)\n" " no - Signal 'no channel available' aka 'call waiting'. (see DSS1)"}, - {"channel-in", &inter_channel_in, "[force,][][,...][,free][,any][,no]", + {"channel-in", &inter_channel_in, "[][,...][,free]", "Channel selection list for all incomming calls from the interface.\n" "A free channels is accepted if in the list.\n" "If any channel was requested, the first free channel found is selected.\n" diff --git a/main.c b/main.c index 2f11938..69d6ab7 100644 --- a/main.c +++ b/main.c @@ -66,6 +66,11 @@ int last_debug = 0; int debug_newline = 1; int nooutput = 0; +void debug_usleep(int msec, char *file, int line, int hour, int min, int sec) +{ + usleep(msec); +} + void debug(const char *function, int line, char *prefix, char *buffer) { /* if we have a new debug count, we add a mark */ @@ -463,10 +468,16 @@ int main(int argc, char *argv[]) /* all loops must be counted from the beginning since nodes might get freed during handler */ all_idle = 1; +#warning debugging usleep crash + debug_usleep(1, __FILE__, __LINE__, now_tm->tm_hour, now_tm->tm_min, now_tm->tm_sec); + /* handle mISDN messages from kernel */ debug_prefix = "ISDN"; if (mISDN_handler()) all_idle = 0; +#warning debugging usleep crash + debug_usleep(1, __FILE__, __LINE__, now_tm->tm_hour, now_tm->tm_min, now_tm->tm_sec); + #ifdef DEBUG_DURATION GET_NOW(); isdn_duration += (now_d - start_d); @@ -638,6 +649,8 @@ BUDETECT all_idle = 0; } #endif +#warning debugging usleep crash + debug_usleep(1, __FILE__, __LINE__, now_tm->tm_hour, now_tm->tm_min, now_tm->tm_sec); /* do idle checking */ if (idlecheck != now) @@ -670,7 +683,7 @@ BUDETECT /* did we do nothing? so we wait to give time to other processes */ if (all_idle) { - usleep(4000); /* wait 32 samples */ + debug_usleep(4000, __FILE__, __LINE__, now_tm->tm_hour, now_tm->tm_min, now_tm->tm_sec); idletime += 4000; } } diff --git a/message.c b/message.c index 7b8ce57..eab2978 100644 --- a/message.c +++ b/message.c @@ -54,7 +54,7 @@ void message_put(struct message *message) messagepointer_end = &(message->next); } -void message_forward(int id_from, int id_to, int flow, union parameter *param) +struct message *message_forward(int id_from, int id_to, int flow, union parameter *param) { struct message *message; @@ -68,6 +68,8 @@ void message_forward(int id_from, int id_to, int flow, union parameter *param) message->id_to = id_to; message->flow = flow; message_put(message); + + return(message); } /* detaches the first messages from the message chain */ diff --git a/message.h b/message.h index ae1e8fd..d60c1b3 100644 --- a/message.h +++ b/message.h @@ -278,6 +278,10 @@ struct param_hello { char application[32]; /* name of remote application */ }; +struct param_bchannel { + unsigned long addr; /* bchannel stack address */ +}; + /* structure of message parameter */ union parameter { struct param_tone tone; /* MESSAGE_TONE */ @@ -300,6 +304,7 @@ union parameter { struct extension ext; /* tell port about extension information */ struct param_crypt crypt; /* MESSAGE_CRYPT */ struct param_hello hello; /* MESSAGE_HELLO */ + struct param_bchannel bchannel; /* MESSAGE_BCHANNEL */ }; enum { /* message flow */ @@ -355,6 +360,7 @@ enum { /* messages between entities */ MESSAGE_TONE_COUNTER, /* tone counter (for VBOX tone use) */ MESSAGE_TONE_EOF, /* tone is end of file */ MESSAGE_BCHANNEL, /* request/assign bchannel */ + MESSAGE_BCHANNEL_FREE, /* requests/assigns bchannel to be free */ MESSAGE_HELLO, /* hello message for remote application */ MESSAGE_NEWREF, /* special message to create and inform ref */ }; @@ -396,7 +402,7 @@ enum { /* messages between entities */ struct message *message_create(int id_from, int id_to, int flow, int type); void message_put(struct message *message); -void message_forward(int id_from, int id_to, int flow, union parameter *param); +struct message *message_forward(int id_from, int id_to, int flow, union parameter *param); struct message *message_get(void); void message_free(struct message *message); diff --git a/route.c b/route.c index 8c158bf..358bf4d 100644 --- a/route.c +++ b/route.c @@ -123,7 +123,7 @@ struct param_defs param_defs[] = { "capability=speech|audio|video|digital-restricted|digital-unrestricted|digital-unrestricted-tones", "Alter the service type of the call."}, { PARAM_BMODE, "bmode", PARAM_TYPE_BMODE, - "capability=transparent|hdlc", "Alter the bchannel mode of the call. Use hdlc for data calls."}, + "bmode=transparent|hdlc", "Alter the bchannel mode of the call. Use hdlc for data calls."}, { PARAM_INFO1, "infolayer1", PARAM_TYPE_INTEGER, "infolayer1=", "Alter the layer 1 information of a call. Use 3 for ALAW or 2 for uLAW."}, @@ -329,11 +329,6 @@ struct action_defs action_defs[] = { "disconnect", NULL, &EndpointAppPBX::action_dialing_disconnect, NULL, PARAM_CONNECT | PARAM_CAUSE | PARAM_LOCATION | PARAM_SAMPLE | PARAM_DISPLAY, "Caller gets disconnected optionally with given cause and given sample and given display text."}, - { ACTION_HELP, - "help", NULL, &EndpointAppPBX::action_dialing_help, NULL, - PARAM_CONNECT | PARAM_TIMEOUT, - NULL}, -// "Caller will be able to select from current rules that would match. (using * and #)"}, { ACTION_DEFLECT, "deflect", NULL, &EndpointAppPBX::action_dialing_deflect, NULL, PARAM_DEST, diff --git a/route.h b/route.h index 7b5fded..b887125 100644 --- a/route.h +++ b/route.h @@ -163,16 +163,15 @@ enum { /* how to parse text file during startup */ #define ACTION_GOTO 20 #define ACTION_MENU 21 #define ACTION_DISCONNECT 22 -#define ACTION_HELP 23 -#define ACTION_DEFLECT 24 -#define ACTION_SETFORWARD 25 -#define ACTION_EXECUTE 26 -#define ACTION_FILE 27 -#define ACTION_PICK 28 -#define ACTION_PASSWORD 29 -#define ACTION_PASSWORD_WRITE 30 -#define ACTION_NOTHING 31 -#define ACTION_EFI 32 +#define ACTION_DEFLECT 23 +#define ACTION_SETFORWARD 24 +#define ACTION_EXECUTE 25 +#define ACTION_FILE 26 +#define ACTION_PICK 27 +#define ACTION_PASSWORD 28 +#define ACTION_PASSWORD_WRITE 29 +#define ACTION_NOTHING 30 +#define ACTION_EFI 31 struct route_cond { /* an item */ struct route_cond *next; /* next entry */ @@ -211,13 +210,14 @@ struct route_rule { /* a rule has a list of items and actions */ int line; /* line parsed from */ struct route_cond *cond_first; /* link to condition list */ struct route_action *action_first; /* link to action list */ +// int temp_couldmatch; /* stores, if the dialing could match. this is used to make a list of rules, that could match */ }; struct route_ruleset { /* the ruleset is a list of rules */ struct route_ruleset *next; /* next item */ char file[128]; /* filename */ int line; /* line parsed from */ - char name[64]; /* name of rule */ + char name[64]; /* name of ruleset */ struct route_rule *rule_first; /* linke to rule list */ };