this recovers 'hang' of bchannel if the reply message got lost due to buffer overflows
fixed some minor warnings
modified: Makefile
modified: README
modified: action_efi.cpp
modified: apppbx.cpp
modified: dss1.cpp
modified: interface.c
modified: mISDN.cpp
modified: mISDN.h
modified: message.h
WIZZARD = ./wizzard
LCR = ./lcr
LCRADMIN = ./lcradmin
WIZZARD = ./wizzard
LCR = ./lcr
LCRADMIN = ./lcradmin
+CFLAGS_LCRADMIN = -DINSTALL_DATA=\"$(INSTALL_DATA)\"
ifdef WITH-ASTERISK
CHAN_LCR = ./chan_lcr
endif
ifdef WITH-ASTERISK
CHAN_LCR = ./chan_lcr
endif
GENW = ./genwave
GENRC = ./genrc
GENEXT = ./genextension
GENW = ./genwave
GENRC = ./genrc
GENEXT = ./genextension
-CFLAGS = -DINSTALL_DATA=\"$(INSTALL_DATA)\" -I/usr/include/mISDNuser/
+CFLAGS = -Wall -g -DINSTALL_DATA=\"$(INSTALL_DATA)\" -I/usr/include/mISDNuser/
#CFLAGS = -Wall -g -DINSTALL_DATA=\"$(INSTALL_DATA)\"
ifdef WITH-CRYPTO
CFLAGS += -DCRYPTO
#CFLAGS = -Wall -g -DINSTALL_DATA=\"$(INSTALL_DATA)\"
ifdef WITH-CRYPTO
CFLAGS += -DCRYPTO
$(LIBS) -o $(LCR)
$(LCRADMIN): lcradmin.c cause.c *.h Makefile
$(LIBS) -o $(LCR)
$(LCRADMIN): lcradmin.c cause.c *.h Makefile
- $(PP) $(LIBDIR) $(CFLAGS) $(CURSES) -lm lcradmin.c cause.c \
+ $(PP) $(LIBDIR) $(CFLAGS_LCRADMIN) $(CURSES) -lm lcradmin.c cause.c \
-o $(LCRADMIN)
$(CHAN_LCR): chan_lcr.o bchannel.o
-o $(LCRADMIN)
$(CHAN_LCR): chan_lcr.o bchannel.o
Changes in Version 0.5
- Preperations for Asterisk channel driver (chan_lcr)
- Errors in information elements are now reported inside log/trace.
Changes in Version 0.5
- Preperations for Asterisk channel driver (chan_lcr)
- Errors in information elements are now reported inside log/trace.
+- Recover bchannel (de-)activation if message from mISDN got lost
{
// char buffer[32];
char digit[] = "number_00";
{
// char buffer[32];
char digit[] = "number_00";
- struct message *message;
- struct port_list *portlist = ea_endpoint->ep_portlist;
+// struct message *message;
+// struct port_list *portlist = ea_endpoint->ep_portlist;
PDEBUG(DEBUG_EPOINT, "EPOINT(%d) terminal %s end of file during state: %d\n", ea_endpoint->ep_serial, e_ext.number, e_vbox_state);
PDEBUG(DEBUG_EPOINT, "EPOINT(%d) terminal %s end of file during state: %d\n", ea_endpoint->ep_serial, e_ext.number, e_vbox_state);
void EndpointAppPBX::join_setup(struct port_list *portlist, int message_type, union parameter *param)
{
struct message *message;
void EndpointAppPBX::join_setup(struct port_list *portlist, int message_type, union parameter *param)
{
struct message *message;
- struct interface *interface;
+// struct interface *interface;
/* if we already in setup state, we just update the dialing with new digits */
if (e_state == EPOINT_STATE_OUT_SETUP
/* if we already in setup state, we just update the dialing with new digits */
if (e_state == EPOINT_STATE_OUT_SETUP
void Pdss1::new_state(int state)
{
void Pdss1::new_state(int state)
{
- class Endpoint *epoint;
+// class Endpoint *epoint;
/* set timeout */
if (state == PORT_STATE_IN_OVERLAP)
/* set timeout */
if (state == PORT_STATE_IN_OVERLAP)
static int inter_timeouts(struct interface *interface, char *filename, int line, char *parameter, char *value)
{
struct interface_port *ifport;
static int inter_timeouts(struct interface *interface, char *filename, int line, char *parameter, char *value)
{
struct interface_port *ifport;
- struct select_channel *selchannel, **selchannelp;
- int val;
+// struct select_channel *selchannel, **selchannelp;
+// int val;
char *p, *el;
/* port in chain ? */
char *p, *el;
/* port in chain ? */
#define ISDN_PID_L4_B_USER 0x440000ff
#endif
#define ISDN_PID_L4_B_USER 0x440000ff
#endif
+// timeouts if activating/deactivating response from mISDN got lost
+#define B_TIMER_ACTIVATING 1
+#define B_TIMER_DEACTIVATING 1
+
/* list of mISDN ports */
struct mISDNport *mISDNport_first;
/* list of mISDN ports */
struct mISDNport *mISDNport_first;
/* trace */
chan_trace_header(mISDNport, mISDNport->b_port[i], activate?(char*)"BCHANNEL activate":(char*)"BCHANNEL deactivate", DIRECTION_OUT);
add_trace("channel", NULL, "%d", i+1+(i>=15));
/* trace */
chan_trace_header(mISDNport, mISDNport->b_port[i], activate?(char*)"BCHANNEL activate":(char*)"BCHANNEL deactivate", DIRECTION_OUT);
add_trace("channel", NULL, "%d", i+1+(i>=15));
+ if (mISDNport->b_timer[i])
+ add_trace("event", NULL, "timeout recovery");
{
class PmISDN *b_port = mISDNport->b_port[i];
int state = mISDNport->b_state[i];
{
class PmISDN *b_port = mISDNport->b_port[i];
int state = mISDNport->b_state[i];
+ double timer = mISDNport->b_timer[i];
unsigned long p_m_remote_ref = 0;
unsigned long p_m_remote_id = 0;
int p_m_tx_gain = 0;
unsigned long p_m_remote_ref = 0;
unsigned long p_m_remote_id = 0;
int p_m_tx_gain = 0;
{
_bchannel_activate(mISDNport, i, 1);
state = B_STATE_ACTIVATING;
{
_bchannel_activate(mISDNport, i, 1);
state = B_STATE_ACTIVATING;
+ timer = now_d + B_TIMER_ACTIVATING;
/* bchannel is active, so we deactivate */
_bchannel_activate(mISDNport, i, 0);
state = B_STATE_DEACTIVATING;
/* bchannel is active, so we deactivate */
_bchannel_activate(mISDNport, i, 0);
state = B_STATE_DEACTIVATING;
+ timer = now_d + B_TIMER_DEACTIVATING;
break;
case B_EVENT_ACTIVATED:
break;
case B_EVENT_ACTIVATED:
switch(state)
{
case B_STATE_ACTIVATING:
switch(state)
{
case B_STATE_ACTIVATING:
/* bchannel is active, but exported OR not used anymore (or has wrong stack config), so we deactivate */
_bchannel_activate(mISDNport, i, 0);
state = B_STATE_DEACTIVATING;
/* bchannel is active, but exported OR not used anymore (or has wrong stack config), so we deactivate */
_bchannel_activate(mISDNport, i, 0);
state = B_STATE_DEACTIVATING;
+ timer = now_d + B_TIMER_DEACTIVATING;
/* bchannel is active, so we deactivate */
_bchannel_activate(mISDNport, i, 0);
state = B_STATE_DEACTIVATING;
/* bchannel is active, so we deactivate */
_bchannel_activate(mISDNport, i, 0);
state = B_STATE_DEACTIVATING;
+ timer = now_d + B_TIMER_DEACTIVATING;
break;
case B_STATE_REMOTE:
break;
case B_STATE_REMOTE:
break;
case B_EVENT_DEACTIVATED:
break;
case B_EVENT_DEACTIVATED:
switch(state)
{
case B_STATE_IDLE:
switch(state)
{
case B_STATE_IDLE:
{
_bchannel_activate(mISDNport, i, 1);
state = B_STATE_ACTIVATING;
{
_bchannel_activate(mISDNport, i, 1);
state = B_STATE_ACTIVATING;
+ timer = now_d + B_TIMER_ACTIVATING;
{
_bchannel_activate(mISDNport, i, 1);
state = B_STATE_ACTIVATING;
{
_bchannel_activate(mISDNport, i, 1);
state = B_STATE_ACTIVATING;
+ timer = now_d + B_TIMER_ACTIVATING;
+ case B_EVENT_TIMEOUT:
+ timer = 0;
+ switch(state)
+ {
+ case B_STATE_IDLE:
+ /* ignore due to deactivation confirm after unloading */
+ break;
+
+ case B_STATE_ACTIVATING:
+ _bchannel_activate(mISDNport, i, 1);
+ timer = now_d + B_TIMER_ACTIVATING;
+ break;
+
+ case B_STATE_DEACTIVATING:
+ _bchannel_activate(mISDNport, i, 0);
+ timer = now_d + B_TIMER_DEACTIVATING;
+ break;
+
+ default:
+ PERROR("Illegal event %d at state %d, please correct.\n", event, state);
+ }
+ break;
+
default:
PERROR("Illegal event %d, please correct.\n", event);
}
mISDNport->b_state[i] = state;
default:
PERROR("Illegal event %d, please correct.\n", event);
}
mISDNport->b_state[i] = state;
+ mISDNport->b_timer[i] = timer;
i = 0;
while(i < mISDNport->b_num)
{
i = 0;
while(i < mISDNport->b_num)
{
+ /* process timer events for bchannel handling */
+ if (mISDNport->b_timer[i])
+ {
+ if (mISDNport->b_timer[i] <= now_d)
+ bchannel_event(mISDNport, i, B_EVENT_TIMEOUT);
+ }
/* handle port of bchannel */
isdnport=mISDNport->b_port[i];
if (isdnport)
/* handle port of bchannel */
isdnport=mISDNport->b_port[i];
if (isdnport)
i = 0;
while(i < mISDNport->b_num)
{
i = 0;
while(i < mISDNport->b_num)
{
+ /* process timer events for bchannel handling */
+ if (mISDNport->b_timer[i])
+ {
+ if (mISDNport->b_timer[i] <= now_d)
+ bchannel_event(mISDNport, i, B_EVENT_TIMEOUT);
+ }
isdnport=mISDNport->b_port[i];
if (isdnport)
{
isdnport=mISDNport->b_port[i];
if (isdnport)
{
unsigned long b_addr[128];
#endif
int b_state[128]; /* statemachine, 0 = IDLE */
unsigned long b_addr[128];
#endif
int b_state[128]; /* statemachine, 0 = IDLE */
+ double b_timer[128]; /* timer for state machine */
unsigned long b_remote_id[128]; /* the socket currently exported */
unsigned long b_remote_ref[128]; /* the ref currently exported */
int procids[128]; /* keep track of free ids */
unsigned long b_remote_id[128]; /* the socket currently exported */
unsigned long b_remote_ref[128]; /* the ref currently exported */
int procids[128]; /* keep track of free ids */
B_EVENT_DEACTIVATED, /* DL_RELEASE received */
B_EVENT_EXPORTED, /* BCHANNEL_ASSIGN received */
B_EVENT_IMPORTED, /* BCHANNEL_REMOVE received */
B_EVENT_DEACTIVATED, /* DL_RELEASE received */
B_EVENT_EXPORTED, /* BCHANNEL_ASSIGN received */
B_EVENT_IMPORTED, /* BCHANNEL_REMOVE received */
+ B_EVENT_TIMEOUT, /* timeout for bchannel state */
/* call-info structure CALLER */
struct caller_info {
char id[32]; /* id of caller (user number) */
/* call-info structure CALLER */
struct caller_info {
char id[32]; /* id of caller (user number) */