backup
[lcr.git] / mISDN.cpp
1 /*****************************************************************************\
2 **                                                                           **
3 ** PBX4Linux                                                                 **
4 **                                                                           **
5 **---------------------------------------------------------------------------**
6 ** Copyright: Andreas Eversberg                                              **
7 **                                                                           **
8 ** mISDN port abstraction for dss1 and sip                                   **
9 **                                                                           **
10 \*****************************************************************************/ 
11
12
13 #include <stdio.h>
14 #include <string.h>
15 #include <stdlib.h>
16 #include "main.h"
17 #include <unistd.h>
18 #include <poll.h>
19 #include <errno.h>
20 #include <sys/ioctl.h>
21 #include <sys/types.h>
22 #include <sys/stat.h>
23 #include <fcntl.h>
24 extern "C" {
25 #include <net_l2.h>
26 }
27
28 #define ISDN_PID_L2_B_USER 0x420000ff
29 #define ISDN_PID_L3_B_USER 0x430000ff
30 #define ISDN_PID_L4_B_USER 0x440000ff
31
32 /* used for udevice */
33 int entity = 0;
34
35 /* noise randomizer */
36 unsigned char mISDN_rand[256];
37 int mISDN_rand_count = 0;
38
39 /* the device handler and port list */
40 int mISDNdevice = -1;
41
42 /* list of mISDN ports */
43 struct mISDNport *mISDNport_first;
44
45 /*
46  * constructor
47  */
48 PmISDN::PmISDN(int type, mISDNport *mISDNport, char *portname, struct port_settings *settings, int channel, int exclusive) : Port(type, portname, settings)
49 {
50         p_m_mISDNport = mISDNport;
51         p_m_portnum = mISDNport->portnum;
52         p_m_b_index = -1;
53         p_m_b_channel = 0;
54         p_m_b_exclusive = 0;
55         p_m_b_reserve = 0;
56         p_m_b_addr = 0;
57         p_m_b_stid = 0;
58         p_m_jittercheck = 0;
59         p_m_delete = 0;
60         p_m_hold = 0;
61         p_m_txvol = p_m_rxvol = 0;
62         p_m_conf = 0;
63         p_m_txdata = 0;
64 #warning set delay by routing parameter or interface config
65         p_m_delay = 0;
66         p_m_echo = 0;
67         p_m_tone = 0;
68         p_m_rxoff = 0;
69         p_m_nodata = 1; /* may be 1, because call always notifies us */
70         p_m_dtmf = !options.nodtmf;
71         sollen wir daraus eine interface-option machen?:
72         p_m_timeout = 0;
73         p_m_timer = 0;
74 #warning denke auch an die andere seite. also das setup sollte dies weitertragen
75
76         p_m_crypt = 0;
77         p_m_crypt_listen = 0;
78         p_m_crypt_msg_loops = 0;
79         p_m_crypt_msg_loops = 0;
80         p_m_crypt_msg_len = 0;
81         p_m_crypt_msg[0] = '\0';
82         p_m_crypt_msg_current = 0;
83         p_m_crypt_key[0] = '\0';
84         p_m_crypt_key_len = 0;
85         p_m_crypt_listen = 0;
86         p_m_crypt_listen_state = 0;
87         p_m_crypt_listen_len = 0;
88         p_m_crypt_listen_msg[0] = '\0';
89         p_m_crypt_listen_crc = 0;
90
91         /* if any channel requested by constructor */
92         if (channel == CHANNEL_ANY)
93         {
94                 /* reserve channel */
95                 p_m_b_reserve = 1;
96                 mISDNport->b_reserved++;
97         }
98
99         } else
100         /* reserve channel */
101         if (channel) // only if constructor was called with a channel resevation
102                 seize_bchannel(channel, exclusive);
103
104         /* we increase the number of objects: */
105         mISDNport->use++;
106         PDEBUG(DEBUG_ISDN, "Created new mISDNPort(%s). Currently %d objects use, port #%d\n", portname, mISDNport->use, p_m_portnum);
107 }
108
109
110 /*
111  * destructor
112  */
113 PmISDN::~PmISDN()
114 {
115         struct message *message;
116
117         /* remove bchannel relation */
118         free_bchannel();
119
120         /* release epoint */
121         while (p_epointlist)
122         {
123                 PDEBUG(DEBUG_ISDN, "destroy mISDNPort(%s). endpoint still exists, releaseing.\n", p_name);
124                 message = message_create(p_serial, p_epointlist->epoint_id, PORT_TO_EPOINT, MESSAGE_RELEASE);
125                 message->param.disconnectinfo.cause = 16;
126                 message->param.disconnectinfo.location = LOCATION_PRIVATE_LOCAL;
127                 message_put(message);
128                 /* remove from list */
129                 free_epointlist(p_epointlist);
130         }
131
132         /* we decrease the number of objects: */
133         p_m_mISDNport->use--;
134         PDEBUG(DEBUG_ISDN, "destroyed mISDNPort(%s). Currently %d objects\n", p_name, p_m_mISDNport->use);
135 }
136
137
138 /*
139  * send control information to the channel (dsp-module)
140  */
141 void ph_control(unsigned long b_addr, int c1, int c2)
142 {
143         unsigned char buffer[mISDN_HEADER_LEN+sizeof(int)+sizeof(int)];
144         iframe_t *ctrl = (iframe_t *)buffer; 
145         unsigned long *d = (unsigned long *)&ctrl->data.p;
146
147         ctrl->prim = PH_CONTROL | REQUEST;
148         ctrl->addr = b_addr | FLG_MSG_DOWN;
149         ctrl->dinfo = 0;
150         ctrl->len = sizeof(unsigned long)*2;
151         *d++ = c1;
152         *d++ = c2;
153         mISDN_write(mISDNdevice, ctrl, mISDN_HEADER_LEN+ctrl->len, TIMEOUT_1SEC);
154 }
155
156 void ph_control_block(unsigned long b_addr, int c1, void *c2, int c2_len)
157 {
158         unsigned char buffer[mISDN_HEADER_LEN+sizeof(int)+c2_len];
159         iframe_t *ctrl = (iframe_t *)buffer;
160         unsigned long *d = (unsigned long *)&ctrl->data.p;
161
162         ctrl->prim = PH_CONTROL | REQUEST;
163         ctrl->addr = b_addr | FLG_MSG_DOWN;
164         ctrl->dinfo = 0;
165         ctrl->len = sizeof(unsigned long)*2;
166         *d++ = c1;
167         memcpy(d, c2, c2_len);
168         mISDN_write(mISDNdevice, ctrl, mISDN_HEADER_LEN+ctrl->len, TIMEOUT_1SEC);
169 }
170
171
172 /*
173  * activate / deactivate bchannel
174  */
175 static void bchannel_activate(struct mISDNport *mISDNport, int i)
176 {
177         iframe_t act;
178
179         /* we must activate if we are deactivated */
180         if (mISDNport->b_state[i] == B_STATE_IDLE)
181         {
182                 /* activate bchannel */
183                 PDEBUG(DEBUG_BCHANNEL, "activating bchannel (index %d), because currently idle (address 0x%x).\n", i, mISDNport->b_addr[i]);
184                 act.prim = DL_ESTABLISH | REQUEST; 
185                 act.addr = mISDNport->b_addr[i] | FLG_MSG_DOWN;
186                 act.dinfo = 0;
187                 act.len = 0;
188                 mISDN_write(mISDNdevice, &act, mISDN_HEADER_LEN+act.len, TIMEOUT_1SEC);
189                 mISDNport->b_state[i] = B_STATE_ACTIVATING;
190                 return;
191         }
192
193         /* if we are active, we configure our channel */
194         if (mISDNport->b_state[i] == B_STATE_ACTIVE)
195         {
196                 unsigned char buffer[mISDN_HEADER_LEN+ISDN_PRELOAD];
197                 iframe_t *pre = (iframe_t *)buffer; /* preload data */
198                 unsigned char *p = (unsigned char *)&pre->data.p;
199
200                 /* it is an error if this channel is not associated with a port object */
201                 if (!mISDNport->b_port[i])
202                 {
203                         PERROR("bchannel index i=%d not associated with a port object\n", i);
204                         return;
205                 }
206
207                 /* configure dsp features */
208                 if (mISDNport->b_port[i]->p_m_txdata)
209                 {
210                         PDEBUG(DEBUG_BCHANNEL, "during activation, we set txdata to txdata=%d.\n", mISDNport->b_port[i]->p_m_txdata);
211                         ph_control(mISDNport->b_addr[i], (mISDNport->b_port[i]->p_m_txdata)?CMX_TXDATA_ON:CMX_TXDATA_OFF);
212                 }
213                 if (mISDNport->b_port[i]->p_m_delay)
214                 {
215                         PDEBUG(DEBUG_BCHANNEL, "during activation, we set delay to delay=%d.\n", mISDNport->b_port[i]->p_m_delay);
216                         ph_control(mISDNport->b_addr[i], CMX_DELAY, mISDNport->b_port[i]->p_m_delay);
217                 }
218                 if (mISDNport->b_port[i]->p_m_txvol)
219                 {
220                         PDEBUG(DEBUG_BCHANNEL, "during activation, we change tx-volume to shift=%d.\n", mISDNport->b_port[i]->p_m_txvol);
221                         ph_control(mISDNport->b_addr[i], VOL_CHANGE_TX, mISDNport->b_port[i]->p_m_txvol);
222                 }
223                 if (mISDNport->b_port[i]->p_m_rxvol)
224                 {
225                         PDEBUG(DEBUG_BCHANNEL, "during activation, we change rx-volume to shift=%d.\n", mISDNport->b_port[i]->p_m_rxvol);
226                         ph_control(mISDNport->b_addr[i], VOL_CHANGE_RX, mISDNport->b_port[i]->p_m_rxvol);
227                 }
228 //tone          if (mISDNport->b_port[i]->p_m_conf && !mISDNport->b_port[i]->p_m_tone)
229                 if (mISDNport->b_port[i]->p_m_conf)
230                 {
231                         PDEBUG(DEBUG_BCHANNEL, "during activation, we change conference to conf=%d.\n", mISDNport->b_port[i]->p_m_conf);
232                         ph_control(mISDNport->b_addr[i], CMX_CONF_JOIN, mISDNport->b_port[i]->p_m_conf);
233                 }
234                 if (mISDNport->b_port[i]->p_m_echo)
235                 {
236                         PDEBUG(DEBUG_BCHANNEL, "during activation, we set echo to echo=%d.\n", mISDNport->b_port[i]->p_m_echo);
237                         ph_control(mISDNport->b_addr[i], CMX_ECHO_ON, 0);
238                 }
239                 if (mISDNport->b_port[i]->p_m_tone)
240                 {
241                         PDEBUG(DEBUG_BCHANNEL, "during activation, we set tone to tone=%d.\n", mISDNport->b_port[i]->p_m_tone);
242                         ph_control(mISDNport->b_addr[i], TONE_PATT_ON, mISDNport->b_port[i]->p_m_tone);
243                 }
244                 if (mISDNport->b_port[i]->p_m_rxoff)
245                 {
246                         PDEBUG(DEBUG_BCHANNEL, "during activation, we set rxoff to rxoff=%d.\n", mISDNport->b_port[i]->p_m_rxoff);
247                         ph_control(mISDNport->b_addr[i], CMX_RECEIVE_OFF, 0);
248                 }
249 #if 0
250                 if (mISDNport->b_port[i]->p_m_txmix)
251                 {
252                         PDEBUG(DEBUG_BCHANNEL, "during activation, we set txmix to txmix=%d.\n", mISDNport->b_port[i]->p_m_txmix);
253                         ph_control(mISDNport->b_addr[i], CMX_MIX_ON, 0);
254                 }
255 #endif
256                 if (mISDNport->b_port[i]->p_m_dtmf)
257                 {
258                         PDEBUG(DEBUG_BCHANNEL, "during activation, we set dtmf to dtmf=%d.\n", mISDNport->b_port[i]->p_m_dtmf);
259                         ph_control(mISDNport->b_addr[i], DTMF_TONE_START, 0);
260                 }
261                 if (mISDNport->b_port[i]->p_m_crypt)
262                 {
263                         PDEBUG(DEBUG_BCHANNEL, "during activation, we set crypt to crypt=%d.\n", mISDNport->b_port[i]->p_m_crypt);
264                         ph_control_block(mISDNport->b_addr[i], BF_ENABLE_KEY, mISDNport->b_port[i]->p_m_crypt_key, mISDNport->b_port[i]->p_m_crypt_key_len);
265                 }
266
267                 /* preload tx-buffer */
268                 pre->len = mISDNport->b_port[i]->read_audio(p, ISDN_PRELOAD, 1);
269                 if (pre->len > 0)
270                 {
271                         PDEBUG(DEBUG_BCHANNEL, "port is activated, we fill our buffer (ISDN_PRELOAD = %d).\n", pre->len);
272                         /* flip bits */
273 #if 0
274                         q = p + pre->len;
275                         while(p != q)
276                                  *p++ = flip[*p];
277 #endif
278                         pre->prim = DL_DATA | REQUEST;
279                         pre->addr = mISDNport->b_addr[i] | FLG_MSG_DOWN;
280                         pre->dinfo = 0;
281                         mISDN_write(mISDNdevice, pre, mISDN_HEADER_LEN+pre->len, TIMEOUT_1SEC);
282                 }
283         }
284 }
285
286 static void bchannel_deactivate(struct mISDNport *mISDNport, int i)
287 {
288         iframe_t dact;
289
290         if (mISDNport->b_state[i] == B_STATE_ACTIVE)
291         {
292                 /* reset dsp features */
293                 if (mISDNport->b_port[i])
294                 {
295                         if (mISDNport->b_port[i]->p_m_delay)
296                         {
297                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset txdata from txdata=%d.\n", mISDNport->b_port[i]->p_m_txdata);
298                                 ph_control(mISDNport->b_addr[i], CMX_TXDATA_OFF, 0);
299                         }
300                         if (mISDNport->b_port[i]->p_m_delay)
301                         {
302                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset delay from delay=%d.\n", mISDNport->b_port[i]->p_m_delay);
303                                 ph_control(mISDNport->b_addr[i], CMX_JITTER, 0);
304                         }
305                         if (mISDNport->b_port[i]->p_m_txvol)
306                         {
307                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset tx-volume from shift=%d.\n", mISDNport->b_port[i]->p_m_txvol);
308                                 ph_control(mISDNport->b_addr[i], VOL_CHANGE_TX, 0);
309                         }
310                         if (mISDNport->b_port[i]->p_m_rxvol)
311                         {
312                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset rx-volume from shift=%d.\n", mISDNport->b_port[i]->p_m_rxvol);
313                                 ph_control(mISDNport->b_addr[i], VOL_CHANGE_RX, 0);
314                         }
315                         if (mISDNport->b_port[i]->p_m_conf)
316                         {
317                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we release conference from conf=%d.\n", mISDNport->b_port[i]->p_m_conf);
318                                 ph_control(mISDNport->b_addr[i], CMX_CONF_SPLIT, 0);
319                         }
320                         if (mISDNport->b_port[i]->p_m_echo)
321                         {
322                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset echo from echo=%d.\n", mISDNport->b_port[i]->p_m_echo);
323                                 ph_control(mISDNport->b_addr[i], CMX_ECHO_OFF, 0);
324                         }
325                         if (mISDNport->b_port[i]->p_m_tone)
326                         {
327                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset tone from tone=%d.\n", mISDNport->b_port[i]->p_m_tone);
328                                 ph_control(mISDNport->b_addr[i], TONE_PATT_OFF, 0);
329                         }
330                         if (mISDNport->b_port[i]->p_m_rxoff)
331                         {
332                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset rxoff from rxoff=%d.\n", mISDNport->b_port[i]->p_m_rxoff);
333                                 ph_control(mISDNport->b_addr[i], CMX_RECEIVE_ON, 0);
334                         }
335 #if 0
336                         if (mISDNport->b_port[i]->p_m_txmix)
337                         {
338                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset txmix from txmix=%d.\n", mISDNport->b_port[i]->p_m_txmix);
339                                 ph_control(mISDNport->b_addr[i], CMX_MIX_OFF, 0);
340                         }
341 #endif
342                         if (mISDNport->b_port[i]->p_m_dtmf)
343                         {
344                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset dtmf from dtmf=%d.\n", mISDNport->b_port[i]->p_m_dtmf);
345                                 ph_control(mISDNport->b_addr[i], DTMF_TONE_STOP, 0);
346                         }
347                         if (mISDNport->b_port[i]->p_m_crypt)
348                         {
349                                 PDEBUG(DEBUG_BCHANNEL, "during deactivation, we reset crypt from crypt=%d.\n", mISDNport->b_port[i]->p_m_dtmf);
350                                 ph_control(mISDNport->b_addr[i], BF_DISABLE, 0);
351                         }
352                 }
353                 /* deactivate bchannel */
354                 PDEBUG(DEBUG_BCHANNEL, "deactivating bchannel (index %d), because currently active.\n", i);
355                 dact.prim = DL_RELEASE | REQUEST; 
356                 dact.addr = mISDNport->b_addr[i] | FLG_MSG_DOWN;
357                 dact.dinfo = 0;
358                 dact.len = 0;
359                 mISDN_write(mISDNdevice, &dact, mISDN_HEADER_LEN+dact.len, TIMEOUT_1SEC);
360                 mISDNport->b_state[i] = B_STATE_DEACTIVATING;
361                 return;
362         }
363 }
364
365
366 /*
367  * check for available channel and reserve+set it.
368  * give channel number or SEL_CHANNEL_ANY or SEL_CHANNEL_NO
369  * give exclusiv flag
370  * returns -(cause value) or x = channel x or 0 = no channel
371  */
372 denke ans aktivieren und deaktivieren
373 int PmISDN::seize_bchannel(int channel, int exclusive)
374 {
375         int i;
376
377         /* the channel is what we have */
378         if (p_m_b_channel == channel)
379                 return(channel);
380
381         /* if channel already in use, release it */
382         if (p_m_b_channel)
383                 drop_bchannel();
384
385         /* if CHANNEL_NO */
386         if (channel==CHANNEL_NO || channel==0)
387                 return(0);
388         
389         /* is channel in range ? */
390         if (channel==16
391          || (channel>p_m_mISDNport->b_num && channel<16)
392          || ((channel-1)>p_m_mISDNport->b_num && channel>16)) /* channel-1 because channel 16 is not counted */
393                 return(-6); /* channel unacceptable */
394
395         /* request exclusive channel */
396         if (exclusive && channel>0)
397         {
398                 i = channel-1-(channel>16);
399                 if (p_m_mISDNport->b_port[i])
400                         return(-44); /* requested channel not available */
401                 goto seize;
402         }
403
404         /* ask for channel */
405         if (channel>0)
406         {
407                 i = channel-1-(channel>16);
408                 if (p_m_mISDNport->b_port[i] == NULL)
409                         goto seize;
410         }
411
412         /* search for channel */
413         i = 0;
414         while(i < p_m_mISDNport->b_num)
415         {
416                 if (!p_m_mISDNport->b_port[i])
417                 {
418                         channel = i+1+(i>=15);
419                         goto seize;
420                 }
421                 i++;
422         }
423         return(-34); /* no free channel */
424
425 seize:
426         /* link Port */
427         p_m_mISDNport->b_port[i] = this;
428         p_m_b_index = i;
429         p_m_b_channel = channel;
430         p_m_b_exclusive = exclusive;
431         p_m_b_stid = p_m_mISDNport->b_stid[i];
432         p_m_b_addr = p_m_mISDNport->b_addr[i];
433         p_m_jittercheck = 0;
434
435         /* reserve channel */
436         if (p_m_b_reserve == 0) // already reserved
437         {
438                 p_m_b_reserve = 1;
439                 mISDNport->b_reserved++;
440         }
441
442         PDEBUG(DEBUG_BCHANNEL, "PmISDN(%s) seizing bchannel %d (index %d)\n", p_name, channel, i);
443
444         return(channel);
445 }
446
447 /*
448  * drop reserved channel and unset it.
449  */
450 void PmISDN::drop_bchannel(void)
451 {
452         /* unreserve channel */
453         if (p_m_b_reserve)
454                 p_m_mISDNport->b_reserved--;
455         p_m_b_reserve = 0;
456
457         /* if not in use */
458         if (!p_m_b_channel)
459                 return;
460
461         PDEBUG(DEBUG_BCHANNEL, "PmISDN(%s) dropping bchannel\n", p_name);
462
463         p_m_mISDNport->b_port[p_m_b_index] = NULL;
464         p_m_b_index = -1;
465         p_m_b_channel = 0;
466         p_m_b_exclusive = 0;
467         p_m_b_addr = 0;
468         p_m_b_stid = 0;
469 }
470
471 /*
472  * handler
473  */
474 int PmISDN::handler(void)
475 {
476         struct message *message;
477
478         // NOTE: deletion is done by the child class
479
480         /* handle timeouts */
481         if (p_m_timeout)
482         {
483                 if (p_m_timer+p_m_timeout < now_d)
484                 {
485                         PDEBUG(DEBUG_ISDN, "(%s) timeout after %d seconds detected (state=%d).\n", p_name, p_m_timeout, p_state);
486                         p_m_timeout = 0;
487                         /* send timeout to endpoint */
488                         message = message_create(p_serial, ACTIVE_EPOINT(p_epointlist), PORT_TO_EPOINT, MESSAGE_TIMEOUT);
489                         message->param.state = p_state;
490                         message_put(message);
491                 }
492                 return(1);
493         }
494         
495         return(0); /* nothing done */
496 }
497
498
499 /*
500  * whenever we get audio data from bchannel, we process it here
501  */
502 void PmISDN::bchannel_receive(iframe_t *frm)
503 {
504         unsigned char *data_temp;
505         unsigned long length_temp;
506         struct message *message;
507         struct timeval tv;
508         struct timezone tz;
509         long long jitter_now;
510         int newlen;
511         unsigned char *p;
512         int l;
513         unsigned long cont;
514 //      iframe_t rsp; /* response to possible indication */
515 #if 0
516 #warning BCHANNEL-DEBUG
517 {
518         // check if we are part of all ports */
519         class Port *port = port_first;
520         while(port)
521         {
522                 if (port==this)
523                         break;
524                 port=port->next;
525         }
526         if (!port)
527         {
528                 PERROR_RUNTIME("**************************************************\n");
529                 PERROR_RUNTIME("*** BCHANNEL-DEBUG: !this! is not in list of ports\n");
530                 PERROR_RUNTIME("**************************************************\n");
531                 return;
532         }
533 }
534 #endif
535
536
537         if (frm->prim == (PH_CONTROL | INDICATION))
538         {
539                 cont = *((unsigned long *)&frm->data.p);
540                 // PDEBUG(DEBUG_PORT, "PmISDN(%s) received a PH_CONTROL INDICATION 0x%x\n", p_name, cont);
541                 if ((cont&(~DTMF_TONE_MASK)) == DTMF_TONE_VAL)
542                 {
543                         message = message_create(p_serial, ACTIVE_EPOINT(p_epointlist), PORT_TO_EPOINT, MESSAGE_DTMF);
544                         message->param.dtmf = cont & DTMF_TONE_MASK;
545                         PDEBUG(DEBUG_PORT, "PmISDN(%s) PH_CONTROL  DTMF digit '%c'\n", p_name, message->param.dtmf);
546                         message_put(message);
547                 }
548                 switch(cont)
549                 {
550                         case BF_REJECT:
551                         message = message_create(p_serial, ACTIVE_EPOINT(p_epointlist), PORT_TO_EPOINT, MESSAGE_CRYPT);
552                         message->param.crypt.type = CC_ERROR_IND;
553                         PDEBUG(DEBUG_PORT, "PmISDN(%s) PH_CONTROL  reject of blowfish.\n", p_name);
554                         message_put(message);
555                         break;
556
557                         case BF_ACCEPT:
558                         message = message_create(p_serial, ACTIVE_EPOINT(p_epointlist), PORT_TO_EPOINT, MESSAGE_CRYPT);
559                         message->param.crypt.type = CC_ACTBF_CONF;
560                         PDEBUG(DEBUG_PORT, "PmISDN(%s) PH_CONTROL  accept of blowfish.\n", p_name);
561                         message_put(message);
562                         break;
563                 }
564                 return;
565         }
566
567         /* calls will not process any audio data unless
568          * the call is connected OR tones feature is enabled.
569          */
570         if (p_state!=PORT_STATE_CONNECT
571          && !p_m_mISDNport->is_tones)
572                 return;
573
574 #if 0
575         /* the bearer capability must be audio in order to send and receive
576          * audio prior or after connect.
577          */
578         if (!(p_bearerinfo.capability&CLASS_CAPABILITY_AUDIO) && p_state!=PORT_STATE_CONNECT)
579                 return;
580 #endif
581
582         /* if rx is off, it may happen that fifos send us pending informations, we just ignore them */
583         if (p_m_rxoff)
584         {
585                 PDEBUG(DEBUG_BCHANNEL, "PmISDN(%s) ignoring data, because rx is turned off\n", p_name);
586                 return;
587         }
588
589         /* randomize and listen to crypt message if enabled */
590         if (p_m_crypt_listen)
591         {
592                 /* the noisy randomizer */
593                 p = (unsigned char *)&frm->data.p;
594                 l = frm->len;
595                 while(l--)
596                         mISDN_rand[mISDN_rand_count & 0xff] += *p++;
597
598                 cryptman_listen_bch((unsigned char *)&frm->data.p, frm->len);
599         }
600
601         /* prevent jitter */
602         gettimeofday(&tv, &tz);
603         jitter_now = tv.tv_sec;
604         jitter_now = jitter_now*8000 + tv.tv_usec/125;
605         if (p_m_jittercheck == 0)
606         {
607                 p_m_jittercheck = jitter_now;
608                 p_m_jitterdropped = 0;
609         } else
610                 p_m_jittercheck += frm->len;
611         if (p_m_jittercheck < jitter_now)
612         {
613 //              PERROR("jitter: ignoring slow data\n");
614                 p_m_jittercheck = jitter_now;
615         } else
616         if (p_m_jittercheck-ISDN_JITTERLIMIT > jitter_now)
617         {
618                 p_m_jitterdropped += frm->len;
619                 p_m_jittercheck -= frm->len;
620                 /* must exit here */
621                 return;
622         } else
623         if (p_m_jitterdropped)
624         {
625                 PERROR("jitter: dropping, caused by fast data: %lld\n", p_m_jitterdropped);
626                 p_m_jitterdropped = 0;
627         }
628
629         p = (unsigned char *)&frm->data.p;
630
631         /* send data to epoint */
632         if (ACTIVE_EPOINT(p_epointlist)) /* only if we have an epoint object */
633         {
634 //printf("we are port %s and sending to epoint %d\n", p_m_cardname, p_epoint->serial);
635                 length_temp = frm->len;
636                 data_temp = p;
637                 while(length_temp)
638                 {
639                         message = message_create(p_serial, ACTIVE_EPOINT(p_epointlist), PORT_TO_EPOINT, MESSAGE_DATA);
640                         message->param.data.len = (length_temp>sizeof(message->param.data.data))?sizeof(message->param.data.data):length_temp;
641                         memcpy(message->param.data.data, data_temp, message->param.data.len);
642                         message->param.data.compressed = 1;
643                         message->param.data.port_id = p_serial;
644                         message->param.data.port_type = p_type;
645                         message_put(message);
646                         if (length_temp <= sizeof(message->param.data.data))
647                                 break;
648                         data_temp += sizeof(message->param.data.data);
649                         length_temp -= sizeof(message->param.data.data);
650                 }
651         }
652         /* return the same number of tone data, as we recieved */
653         newlen = read_audio(p, frm->len, 1);
654         /* send tone data to isdn device only if we have data, otherwhise we send nothing */
655         if (newlen>0 && (p_tone_fh>=0 || p_tone_fetched || !p_m_nodata || p_m_crypt_msg_loops))
656         {
657 //printf("jolly: sending.... %d %d %d %d %d\n", newlen, p_tone_fh, p_tone_fetched, p_m_nodata, p_m_crypt_msg_loops);
658 #if 0
659                 if (p_m_txmix_on)
660                 {
661                         p_m_txmix_on -= newlen;
662                         if (p_m_txmix_on <= 0)
663                         {
664                                 p_m_txmix_on = 0;
665                                 p_m_txmix = !p_m_nodata;
666                                 PDEBUG(DEBUG_BCHANNEL, "after sending message, we set txmix to txmix=%d.\n", p_m_txmix);
667                                 if (p_m_txmix)
668                                         ph_control(p_m_b_addr, CMX_MIX_ON, 0);
669                         }
670                 }
671 #endif 
672                 if (p_m_crypt_msg_loops)
673                 {
674                         /* send pending message */
675                         int tosend;
676
677                         tosend = p_m_crypt_msg_len - p_m_crypt_msg_current;
678                         if (tosend > newlen)
679                                 tosend = newlen;
680                         memcpy(p, p_m_crypt_msg+p_m_crypt_msg_current, tosend);
681                         p_m_crypt_msg_current += tosend;
682                         if (p_m_crypt_msg_current == p_m_crypt_msg_len)
683                         {
684                                 p_m_crypt_msg_current = 0;
685                                 p_m_crypt_msg_loops--;
686 #if 0
687 // we need to disable rxmix some time after sending the loops...
688                                 if (!p_m_crypt_msg_loops && p_m_txmix)
689                                 {
690                                         p_m_txmix_on = 8000; /* one sec */
691                                 }
692 #endif
693                         }
694                 }
695                 frm->prim = frm->prim & 0xfffffffc | REQUEST; 
696                 frm->addr = p_m_b_addr | FLG_MSG_DOWN;
697                 frm->len = newlen;
698                 mISDN_write(mISDNdevice, frm, mISDN_HEADER_LEN+frm->len, TIMEOUT_1SEC);
699
700                 if (p_debug_nothingtosend)
701                 {
702                         p_debug_nothingtosend = 0;
703                         PDEBUG((DEBUG_PORT | DEBUG_BCHANNEL), "PmISDN(%s) start sending, because we have tones and/or remote audio.\n", p_name);
704                 } 
705         } else
706         {
707                 if (!p_debug_nothingtosend)
708                 {
709                         p_debug_nothingtosend = 1;
710                         PDEBUG((DEBUG_PORT | DEBUG_BCHANNEL), "PmISDN(%s) stop sending, because we have only silence.\n", p_name);
711                 } 
712         }
713 #if 0
714         /* response to the data indication */
715         rsp.prim = frm->prim & 0xfffffffc | RESPONSE; 
716         rsp.addr = frm->addr & INST_ID_MASK | FLG_MSG_DOWN;
717         rsp.dinfo = frm->dinfo;
718         rsp.len = 0;
719         mISDN_write(mISDNdevice, &rsp, mISDN_HEADER_LEN+rsp.len, TIMEOUT_1SEC);
720 //PDEBUG(DEBUG_ISDN, "written %d bytes.\n", length);
721 #endif
722 }
723
724
725 /*
726  * set echotest
727  */
728 void PmISDN::set_echotest(int echo)
729 {
730         if (p_m_echo != echo)
731         {
732                 p_m_echo = echo;
733                 PDEBUG(DEBUG_ISDN, "we set echo to echo=%d.\n", p_m_echo);
734                 if (p_m_b_channel)
735                         if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
736                                 ph_control(p_m_b_addr, p_m_echo?CMX_ECHO_ON:CMX_ECHO_OFF, 0);
737         }
738 }
739
740 /*
741  * set tone
742  */
743 void PmISDN::set_tone(char *dir, char *tone)
744 {
745         int id;
746
747         if (!tone)
748                 tone = "";
749         PDEBUG(DEBUG_ISDN, "isdn port now plays tone:'%s'.\n", tone);
750         if (!tone[0])
751         {
752                 id = TONE_OFF;
753                 goto setdsp;
754         }
755
756         /* check if we NOT really have to use a dsp-tone */
757         if (!options.dsptones)
758         {
759                 nodsp:
760                 if (p_m_tone)
761                 if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
762                 {
763                         PDEBUG(DEBUG_ISDN, "we reset tone from id=%d to OFF.\n", p_m_tone);
764                         ph_control(p_m_b_addr, TONE_PATT_OFF, 0);
765                 }
766                 p_m_tone = 0;
767                 Port::set_tone(dir, tone);
768                 return;
769         }
770         if (p_tone_dir[0])
771                 goto nodsp;
772
773         /* now we USE dsp-tone, convert name */
774         else if (!strcmp(tone, "dialtone"))
775         {
776                 switch(options.dsptones) {
777                 case DSP_AMERICAN: id = TONE_AMERICAN_DIALTONE; break;
778                 case DSP_GERMAN: id = TONE_GERMAN_DIALTONE; break;
779                 case DSP_OLDGERMAN: id = TONE_GERMAN_OLDDIALTONE; break;
780                 }
781         } else if (!strcmp(tone, "dialpbx"))
782         {
783                 switch(options.dsptones) {
784                 case DSP_AMERICAN: id = TONE_AMERICAN_DIALPBX; break;
785                 case DSP_GERMAN: id = TONE_GERMAN_DIALPBX; break;
786                 case DSP_OLDGERMAN: id = TONE_GERMAN_OLDDIALPBX; break;
787                 }
788         } else if (!strcmp(tone, "ringing"))
789         {
790                 switch(options.dsptones) {
791                 case DSP_AMERICAN: id = TONE_AMERICAN_RINGING; break;
792                 case DSP_GERMAN: id = TONE_GERMAN_RINGING; break;
793                 case DSP_OLDGERMAN: id = TONE_GERMAN_OLDRINGING; break;
794                 }
795         } else if (!strcmp(tone, "ringpbx"))
796         {
797                 switch(options.dsptones) {
798                 case DSP_AMERICAN: id = TONE_AMERICAN_RINGPBX; break;
799                 case DSP_GERMAN: id = TONE_GERMAN_RINGPBX; break;
800                 case DSP_OLDGERMAN: id = TONE_GERMAN_OLDRINGPBX; break;
801                 }
802         } else if (!strcmp(tone, "busy"))
803         {
804                 busy:
805                 switch(options.dsptones) {
806                 case DSP_AMERICAN: id = TONE_AMERICAN_BUSY; break;
807                 case DSP_GERMAN: id = TONE_GERMAN_BUSY; break;
808                 case DSP_OLDGERMAN: id = TONE_GERMAN_OLDBUSY; break;
809                 }
810         } else if (!strcmp(tone, "release"))
811         {
812                 hangup:
813                 switch(options.dsptones) {
814                 case DSP_AMERICAN: id = TONE_AMERICAN_HANGUP; break;
815                 case DSP_GERMAN: id = TONE_GERMAN_HANGUP; break;
816                 case DSP_OLDGERMAN: id = TONE_GERMAN_OLDHANGUP; break;
817                 }
818         } else if (!strcmp(tone, "cause_10"))
819                 goto hangup;
820         else if (!strcmp(tone, "cause_11"))
821                 goto busy;
822         else if (!strcmp(tone, "cause_22"))
823         {
824                 switch(options.dsptones) {
825                 case DSP_AMERICAN: id = TONE_SPECIAL_INFO; break;
826                 case DSP_GERMAN: id = TONE_GERMAN_GASSENBESETZT; break;
827                 case DSP_OLDGERMAN: id = TONE_GERMAN_OLDBUSY; break;
828                 }
829         } else if (!strncmp(tone, "cause_", 6))
830                 id = TONE_SPECIAL_INFO;
831         else
832                 id = TONE_OFF;
833
834         /* if we have a tone that is not supported by dsp */
835         if (id==TONE_OFF && tone[0])
836                 goto nodsp;
837
838         setdsp:
839         if (p_m_tone != id)
840         {
841                 /* set new tone */
842                 p_m_tone = id;
843                 PDEBUG(DEBUG_ISDN, "we set tone to id=%d.\n", p_m_tone);
844                 if (p_m_b_channel)
845                         if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
846                                 ph_control(p_m_b_addr, p_m_tone?TONE_PATT_ON:TONE_PATT_OFF, p_m_tone);
847         }
848         /* turn user-space tones off in cases of no tone OR dsp tone */
849         Port::set_tone("",NULL);
850 }
851
852
853 /* MESSAGE_mISDNSIGNAL */
854 //extern struct message *dddebug;
855 void PmISDN::message_mISDNsignal(unsigned long epoint_id, int message_id, union parameter *param)
856 {
857         switch(param->mISDNsignal.message)
858         {
859                 case mISDNSIGNAL_VOLUME:
860                 if (p_m_txvol != param->mISDNsignal.txvol)
861                 {
862                         p_m_txvol = param->mISDNsignal.txvol;
863                         PDEBUG(DEBUG_BCHANNEL, "we change tx-volume to shift=%d.\n", p_m_txvol);
864                         if (p_m_b_channel)
865                                 if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
866                                         ph_control(p_m_b_addr, VOL_CHANGE_TX, p_m_txvol);
867                 }
868                 if (p_m_rxvol != param->mISDNsignal.rxvol)
869                 {
870                         p_m_rxvol = param->mISDNsignal.rxvol;
871                         PDEBUG(DEBUG_BCHANNEL, "we change rx-volume to shift=%d.\n", p_m_rxvol);
872                         if (p_m_b_channel)
873                                 if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
874                                         ph_control(p_m_b_addr, VOL_CHANGE_RX, p_m_rxvol);
875                 }
876                 break;
877
878                 case mISDNSIGNAL_CONF:
879 //if (dddebug) PDEBUG(DEBUG_ISDN, "dddebug = %d\n", dddebug->type);
880 //tone          if (!p_m_tone && p_m_conf!=param->mISDNsignal.conf)
881                 if (p_m_conf != param->mISDNsignal.conf)
882                 {
883                         p_m_conf = param->mISDNsignal.conf;
884                         PDEBUG(DEBUG_BCHANNEL, "we change conference to conf=%d.\n", p_m_conf);
885                         if (p_m_b_channel)
886                                 if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
887                                         ph_control(p_m_b_addr, (p_m_conf)?CMX_CONF_JOIN:CMX_CONF_SPLIT, p_m_conf);
888                 }
889                 /* we must set, even if currently tone forbids conf */
890                 p_m_conf = param->mISDNsignal.conf;
891 //if (dddebug) PDEBUG(DEBUG_ISDN, "dddebug = %d\n", dddebug->type);
892                 break;
893
894                 case mISDNSIGNAL_CALLDATA:
895                 if (p_m_calldata != param->mISDNsignal.calldata)
896                 {
897                         p_m_calldata = param->mISDNsignal.calldata;
898                         PDEBUG(DEBUG_BCHANNEL, "we change to calldata=%d.\n", p_m_calldata);
899                         auch senden
900                 }
901                 break;
902                 
903 #if 0
904                 case mISDNSIGNAL_NODATA:
905                 p_m_nodata = param->mISDNsignal.nodata;
906                 if (p_m_txmix == p_m_nodata) /* txmix != !nodata */
907                 {
908                         p_m_txmix = !p_m_nodata;
909                         PDEBUG(DEBUG_BCHANNEL, "we change mix mode to txmix=%d (nodata=%d).\n", p_m_txmix, p_m_nodata);
910                         if (p_m_b_channel)
911                                 if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
912                                         ph_control(p_m_b_addr, p_m_txmix?CMX_MIX_ON:CMX_MIX_OFF, 0);
913                 }
914                 break;
915 #endif
916
917 #if 0
918                 case mISDNSIGNAL_RXOFF:
919                 if (p_m_rxoff != param->mISDNsignal.rxoff)
920                 {
921                         p_m_rxoff = param->mISDNsignal.rxoff;
922                         PDEBUG(DEBUG_BCHANNEL, "we change receive mode to rxoff=%d.\n", p_m_rxoff);
923                         if (p_m_b_channel)
924                                 if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
925                                         ph_control(p_m_b_addr, p_m_rxoff?CMX_RECEIVE_OFF:CMX_RECEIVE_ON, 0);
926                 }
927                 break;
928
929                 case mISDNSIGNAL_DTMF:
930                 if (p_m_dtmf != param->mISDNsignal.dtmf)
931                 {
932                         p_m_dtmf = param->mISDNsignal.dtmf;
933                         PDEBUG(DEBUG_BCHANNEL, "we change dtmf mode to dtmf=%d.\n", p_m_dtmf);
934                         if (p_m_b_channel)
935                                 if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
936                                         ph_control(p_m_b_addr, p_m_dtmf?DTMF_TONE_START:DTMF_TONE_STOP, 0);
937                 }
938                 break;
939
940 #endif
941                 default:
942                 PERROR("PmISDN(%s) unsupported signal message %d.\n", p_name, param->mISDNsignal.message);
943         }
944 }
945
946 /* MESSAGE_CRYPT */
947 void PmISDN::message_crypt(unsigned long epoint_id, int message_id, union parameter *param)
948 {
949         struct message *message;
950
951         switch(param->crypt.type)
952         {
953                 case CC_ACTBF_REQ:           /* activate blowfish */
954                 p_m_crypt = 1;
955                 p_m_crypt_key_len = param->crypt.len;
956                 if (p_m_crypt_key_len > (int)sizeof(p_m_crypt_key))
957                 {
958                         PERROR("PmISDN(%s) key too long %d > %d\n", p_name, p_m_crypt_key_len, sizeof(p_m_crypt_key));
959                         message = message_create(p_serial, ACTIVE_EPOINT(p_epointlist), PORT_TO_EPOINT, MESSAGE_CRYPT);
960                         message->param.crypt.type = CC_ERROR_IND;
961                         message_put(message);
962                         break;
963                 }
964                 memcpy(p_m_crypt_key, param->crypt.data, p_m_crypt_key_len);
965                 crypt_off:
966                 PDEBUG(DEBUG_BCHANNEL, "we set encryption to crypt=%d. (0 means OFF)\n", p_m_crypt);
967                 if (p_m_b_channel)
968                         if (p_m_mISDNport->b_state[p_m_b_index] == B_STATE_ACTIVE)
969                                 ph_control_block(p_m_b_addr, p_m_crypt?BF_ENABLE_KEY:BF_DISABLE, p_m_crypt_key, p_m_crypt_key_len);
970                 break;
971
972                 case CC_DACT_REQ:            /* deactivate session encryption */
973                 p_m_crypt = 0;
974                 goto crypt_off;
975                 break;
976
977                 case CR_LISTEN_REQ:          /* start listening to messages */
978                 p_m_crypt_listen = 1;
979                 p_m_crypt_listen_state = 0;
980                 break;
981
982                 case CR_UNLISTEN_REQ:        /* stop listening to messages */
983                 p_m_crypt_listen = 0;
984                 break;
985
986                 case CR_MESSAGE_REQ:         /* send message */
987                 p_m_crypt_msg_len = cryptman_encode_bch(param->crypt.data, param->crypt.len, p_m_crypt_msg, sizeof(p_m_crypt_msg));
988                 if (!p_m_crypt_msg_len)
989                 {
990                         PERROR("PmISDN(%s) message too long %d > %d\n", p_name, param->crypt.len-1, sizeof(p_m_crypt_msg));
991                         break;
992                 }
993                 p_m_crypt_msg_current = 0; /* reset */
994                 p_m_crypt_msg_loops = 3; /* enable */
995 #if 0
996                 /* disable txmix, or we get corrupt data due to audio process */
997                 if (p_m_txmix)
998                 {
999                         PDEBUG(DEBUG_BCHANNEL, "for sending CR_MESSAGE_REQ, we reset txmix from txmix=%d.\n", p_m_txmix);
1000                         ph_control(p_m_b_addr, CMX_MIX_OFF, 0);
1001                 }
1002 #endif
1003                 break;
1004
1005                 default:
1006                 PERROR("PmISDN(%s) unknown crypt message %d\n", p_name, param->crypt.type);
1007         }
1008
1009 }
1010
1011 /*
1012  * endpoint sends messages to the port
1013  */
1014 int PmISDN::message_epoint(unsigned long epoint_id, int message_id, union parameter *param)
1015 {
1016         if (Port::message_epoint(epoint_id, message_id, param))
1017                 return(1);
1018
1019         switch(message_id)
1020         {
1021                 case MESSAGE_mISDNSIGNAL: /* user command */
1022                 PDEBUG(DEBUG_ISDN, "PmISDN(%s) received special ISDN SIGNAL %d.\n", p_name, param->mISDNsignal.message);
1023                 message_mISDNsignal(epoint_id, message_id, param);
1024                 return(1);
1025
1026                 case MESSAGE_CRYPT: /* crypt control command */
1027                 PDEBUG(DEBUG_ISDN, "PmISDN(%s) received encryption command '%d'.\n", p_name, param->crypt.type);
1028                 message_crypt(epoint_id, message_id, param);
1029                 return(1);
1030         }
1031
1032         return(0);
1033 }
1034
1035
1036 /*
1037  * main loop for processing messages from mISDN device
1038  */
1039 int mISDN_handler(void)
1040 {
1041         int ret;
1042         msg_t *msg;
1043         iframe_t *frm;
1044         struct mISDNport *mISDNport;
1045         class PmISDN *isdnport;
1046         net_stack_t *nst;
1047         msg_t *dmsg;
1048         mISDNuser_head_t *hh;
1049         int i;
1050
1051         if ((ret = Port::handler()))
1052                 return(ret);
1053
1054         /* the que avoids loopbacks when replying to stack after receiving
1055          * from stack. */
1056         mISDNport = mISDNport_first;
1057         while(mISDNport)
1058         {
1059                 /* process turning off rx */
1060                 i = 0;
1061                 while(i < mISDNport->b_num)
1062                 {
1063                         if (mISDNport->b_port[i] && mISDNport->b_state[i] == B_STATE_ACTIVE)
1064                         {
1065                                 isdnport=mISDNport->b_port[i];
1066                                 if (isdnport->p_tone_name[0] || isdnport->p_tone_fh>=0 || isdnport->p_tone_fetched || !isdnport->p_m_nodata || isdnport->p_m_crypt_msg_loops || isdnport->p_m_crypt_listen || isdnport->p_record)
1067                                 {
1068                                         /* rx IS required */
1069                                         if (isdnport->p_m_rxoff)
1070                                         {
1071                                                 /* turn on RX */
1072                                                 isdnport->p_m_rxoff = 0;
1073                                                 PDEBUG(DEBUG_BCHANNEL, "%s: receive data is required, so we turn them on\n");
1074                                                 ph_control(isdnport->p_m_b_addr, CMX_RECEIVE_ON, 0);
1075                                         }
1076                                 } else
1077                                 {
1078                                         /* rx NOT required */
1079                                         if (!isdnport->p_m_rxoff)
1080                                         {
1081                                                 /* turn off RX */
1082                                                 isdnport->p_m_rxoff = 1;
1083                                                 PDEBUG(DEBUG_BCHANNEL, "%s: receive data is not required, so we turn them off\n");
1084                                                 ph_control(isdnport->p_m_b_addr, CMX_RECEIVE_OFF, 0);
1085                                         }
1086                                 }
1087                                 isdnport->p_m_jittercheck = 0; /* reset jitter detection check */
1088                         }
1089                         i++;
1090                 }
1091 #if 0
1092                 if (mISDNport->l1timeout && now>mISDNport->l1timeout)
1093                 {
1094                         PDEBUG(DEBUG_ISDN, "the L1 establish timer expired, we release all pending messages.\n", mISDNport->portnum);
1095                         mISDNport->l1timeout = 0;
1096 #endif
1097
1098                 if (mISDNport->l2establish)
1099                 {
1100                         if (now-mISDNport->l2establish > 5)
1101                         {
1102                                 if (mISDNport->ntmode)
1103                                 {
1104                                         PDEBUG(DEBUG_ISDN, "the L2 establish timer expired, we try to establish the link NT portnum=%d.\n", mISDNport->portnum);
1105                                         time(&mISDNport->l2establish);
1106                                         /* establish */
1107                                         dmsg = create_l2msg(DL_ESTABLISH | REQUEST, 0, 0);
1108                                         if (mISDNport->nst.manager_l3(&mISDNport->nst, dmsg))
1109                                                 free_msg(dmsg);
1110                                 } else {
1111                                         PDEBUG(DEBUG_ISDN, "the L2 establish timer expired, we try to establish the link TE portnum=%d.\n", mISDNport->portnum);
1112                                         time(&mISDNport->l2establish);
1113                                         /* establish */
1114                                         iframe_t act;
1115                                         act.prim = DL_ESTABLISH | REQUEST; 
1116                                         act.addr = (mISDNport->upper_id & ~LAYER_ID_MASK) | 3 | FLG_MSG_DOWN;
1117                                         act.dinfo = 0;
1118                                         act.len = 0;
1119                                         mISDN_write(mISDNdevice, &act, mISDN_HEADER_LEN+act.len, TIMEOUT_1SEC);
1120                                 }
1121                         }
1122                 }
1123                 if ((dmsg = msg_dequeue(&mISDNport->downqueue)))
1124                 {
1125                         if (mISDNport->ntmode)
1126                         {
1127                                 hh = (mISDNuser_head_t *)dmsg->data;
1128                                 PDEBUG(DEBUG_ISDN, "sending queued NT l3-down-message: prim(0x%x) dinfo(0x%x) msg->len(%d)\n", hh->prim, hh->dinfo, dmsg->len);
1129                                 if (mISDNport->nst.manager_l3(&mISDNport->nst, dmsg))
1130                                         free_msg(dmsg);
1131                         } else
1132                         {
1133                                 frm = (iframe_t *)dmsg->data;
1134                                 frm->addr = mISDNport->upper_id | FLG_MSG_DOWN;
1135                                 frm->len = (dmsg->len) - mISDN_HEADER_LEN;
1136                                 PDEBUG(DEBUG_ISDN, "sending queued TE l3-down-message: prim(0x%x) dinfo(0x%x) msg->len(%d)\n", frm->prim, frm->dinfo, dmsg->len);
1137                                 mISDN_write(mISDNdevice, dmsg->data, dmsg->len, TIMEOUT_1SEC);
1138                                 free_msg(dmsg);
1139                         }
1140                         return(1);
1141                 }
1142                 mISDNport = mISDNport->next;
1143         } 
1144
1145         /* get message from kernel */
1146         if (!(msg = alloc_msg(MAX_MSG_SIZE)))
1147                 return(1);
1148         ret = mISDN_read(mISDNdevice, msg->data, MAX_MSG_SIZE, 0);
1149         if (ret < 0)
1150         {
1151                 free_msg(msg);
1152                 if (errno == EAGAIN)
1153                         return(0);
1154                 PERROR("FATAL ERROR: failed to do mISDN_read()\n");
1155                 exit(-1); 
1156         }
1157         if (!ret)
1158         {
1159                 free_msg(msg);
1160 //              printf("%s: ERROR: mISDN_read() returns nothing\n");
1161                 return(0);
1162         }
1163         msg->len = ret;
1164         frm = (iframe_t *)msg->data;
1165
1166         /* global prim */
1167         switch(frm->prim)
1168         {
1169                 case MGR_INITTIMER | CONFIRM:
1170                 case MGR_ADDTIMER | CONFIRM:
1171                 case MGR_DELTIMER | CONFIRM:
1172                 case MGR_REMOVETIMER | CONFIRM:
1173 //              if (options.deb & DEBUG_ISDN)
1174 //                      PDEBUG(DEBUG_ISDN, "timer-confirm\n");
1175                 free_msg(msg);
1176                 return(1);
1177         }
1178
1179         /* find the port */
1180         mISDNport = mISDNport_first;
1181         while(mISDNport)
1182         {
1183                 if ((frm->prim==(MGR_TIMER | INDICATION)) && mISDNport->ntmode)
1184                 {
1185                         itimer_t *it = mISDNport->nst.tlist;
1186
1187                         /* find timer */
1188                         while(it)
1189                         {
1190                                 if (it->id == (int)frm->addr)
1191                                         break;
1192                                 it = it->next;
1193                         }
1194                         if (it)
1195                         {
1196                                 mISDN_write_frame(mISDNdevice, msg->data, mISDNport->upper_id | FLG_MSG_DOWN,
1197                                         MGR_TIMER | RESPONSE, 0, 0, NULL, TIMEOUT_1SEC);
1198
1199                                 PDEBUG(DEBUG_ISDN, "timer-indication %s port %d it=%p\n", (mISDNport->ntmode)?"NT":"TE", mISDNport->portnum, it);
1200                                 test_and_clear_bit(FLG_TIMER_RUNING, (long unsigned int *)&it->Flags);
1201                                 ret = it->function(it->data);
1202                                 break;
1203                         }
1204                         /* we will continue here because we have a timer for a different mISDNport */
1205                 }
1206 //printf("comparing frm->addr %x with upper_id %x\n", frm->addr, mISDNport->upper_id);
1207                 if ((frm->addr&STACK_ID_MASK) == (unsigned int)(mISDNport->upper_id&STACK_ID_MASK))
1208                 {
1209                         /* d-message */
1210                         switch(frm->prim)
1211                         {
1212                                 case MGR_SHORTSTATUS | INDICATION:
1213                                 case MGR_SHORTSTATUS | CONFIRM:
1214                                 switch(frm->dinfo) {
1215                                         case SSTATUS_L1_ACTIVATED:
1216                                         PDEBUG(DEBUG_ISDN, "Received SSTATUS_L1_ACTIVATED for port %d (%s).\n", mISDNport->portnum, mISDNport->ifport->interface->name);
1217                                         goto ss_act;
1218                                         case SSTATUS_L1_DEACTIVATED:
1219                                         PDEBUG(DEBUG_ISDN, "Received SSTATUS_L1_DEACTIVATED for port %d (%s).\n", mISDNport->portnum, mISDNport->ifport->interface->name);
1220                                         goto ss_deact;
1221                                         case SSTATUS_L2_ESTABLISHED:
1222                                         PDEBUG(DEBUG_ISDN, "Received SSTATUS_L2_ESTABLISHED for port %d (%s).\n", mISDNport->portnum, mISDNport->ifport->interface->name);
1223                                         goto ss_estab;
1224                                         case SSTATUS_L2_RELEASED:
1225                                         PDEBUG(DEBUG_ISDN, "Received SSTATUS_L2_RELEASED for port %d (%s).\n", mISDNport->portnum, mISDNport->ifport->interface->name);
1226                                         goto ss_rel;
1227                                 }
1228                                 break;
1229
1230                                 case PH_ACTIVATE | CONFIRM:
1231                                 case PH_ACTIVATE | INDICATION:
1232                                 PDEBUG(DEBUG_ISDN, "Received PH_ACTIVATED for port %d (%s).\n", mISDNport->portnum, mISDNport->ifport->interface->name);
1233                                 if (mISDNport->ntmode)
1234                                 {
1235                                         mISDNport->l1link = 1;
1236                                         setup_queue(mISDNport, 1);
1237                                         goto l1_msg;
1238                                 }
1239                                 ss_act:
1240                                 mISDNport->l1link = 1;
1241                                 setup_queue(mISDNport, 1);
1242                                 break;
1243
1244                                 case PH_DEACTIVATE | CONFIRM:
1245                                 case PH_DEACTIVATE | INDICATION:
1246                                 PDEBUG(DEBUG_ISDN, "Received PH_DEACTIVATED for port %d (%s).\n", mISDNport->portnum, mISDNport->ifport->interface->name);
1247                                 if (mISDNport->ntmode)
1248                                 {
1249                                         mISDNport->l1link = 0;
1250                                         setup_queue(mISDNport, 0);
1251                                         goto l1_msg;
1252                                 }
1253                                 ss_deact:
1254                                 mISDNport->l1link = 0;
1255                                 setup_queue(mISDNport, 0);
1256                                 break;
1257
1258                                 case PH_CONTROL | CONFIRM:
1259                                 case PH_CONTROL | INDICATION:
1260                                 PDEBUG(DEBUG_ISDN, "Received PH_CONTROL for port %d (%s).\n", mISDNport->portnum, mISDNport->ifport->interface->name);
1261                                 break;
1262
1263                                 case DL_ESTABLISH | INDICATION:
1264                                 case DL_ESTABLISH | CONFIRM:
1265 //                              PDEBUG(DEBUG_ISDN, "addr 0x%x established data link (DL) TE portnum=%d (DL_ESTABLISH)\n", frm->addr, mISDNport->portnum);
1266                                 if (!mISDNport->ntmode) break; /* !!!!!!!!!!!!!!!! */
1267                                 ss_estab:
1268 //                              if (mISDNport->ntmode)
1269 //                                      break;
1270                                 if (mISDNport->l2establish)
1271                                 {
1272                                         mISDNport->l2establish = 0;
1273                                         PDEBUG(DEBUG_ISDN, "the link became active before l2establish timer expiry.\n");
1274                                 }
1275                                 mISDNport->l2link = 1;
1276                                 break;
1277
1278                                 case DL_RELEASE | INDICATION:
1279                                 case DL_RELEASE | CONFIRM:
1280 //                              PDEBUG(DEBUG_ISDN, "addr 0x%x released data link (DL) TE portnum=%d (DL_RELEASE)\n", frm->addr, mISDNport->portnum);
1281                                 if (!mISDNport->ntmode) break; /* !!!!!!!!!!!!!!!! */
1282                                 ss_rel:
1283 //                              if (mISDNport->ntmode)
1284 //                                      break;
1285                                 mISDNport->l2link = 0;
1286                                 if (mISDNport->ptp)
1287                                 {
1288                                         time(&mISDNport->l2establish);
1289                                         PDEBUG(DEBUG_ISDN, "because we are ptp, we set a l2establish timer.\n");
1290                                 }
1291                                 break;
1292
1293                                 default:
1294                                 l1_msg:
1295                                 PDEBUG(DEBUG_STACK, "GOT d-msg from %s port %d prim 0x%x dinfo 0x%x addr 0x%x\n", (mISDNport->ntmode)?"NT":"TE", mISDNport->portnum, frm->prim, frm->dinfo, frm->addr);
1296                                 if (frm->dinfo==(signed long)0xffffffff && frm->prim==(PH_DATA|CONFIRM))
1297                                 {
1298                                         PERROR("SERIOUS BUG, dinfo == 0xffffffff, prim == PH_DATA | CONFIRM !!!!\n");
1299                                 }
1300                                 /* d-message */
1301                                 if (mISDNport->ntmode)
1302                                 {
1303                                         /* l1-data enters the nt-mode library */
1304                                         nst = &mISDNport->nst;
1305                                         if (nst->l1_l2(nst, msg))
1306                                                 free_msg(msg);
1307                                         return(1);
1308                                 } else
1309                                 {
1310                                         /* l3-data is sent to pbx */
1311                                         if (stack2manager_te(mISDNport, msg))
1312                                                 free_msg(msg);
1313                                         return(1);
1314                                 }
1315                         }
1316                         break;
1317                 }
1318 //PDEBUG(DEBUG_ISDN, "flg:%d upper_id=%x addr=%x\n", (frm->addr&FLG_CHILD_STACK), (mISDNport->b_addr[0])&(~IF_CHILDMASK), (frm->addr)&(~IF_CHILDMASK));
1319                 /* check if child, and if parent stack match */
1320                 if ((frm->addr&FLG_CHILD_STACK) && (((unsigned int)(mISDNport->b_addr[0])&(~CHILD_ID_MASK)&STACK_ID_MASK) == ((frm->addr)&(~CHILD_ID_MASK)&STACK_ID_MASK)))
1321                 {
1322                         /* b-message */
1323                         switch(frm->prim)
1324                         {
1325                                 /* we don't care about confirms, we use rx data to sync tx */
1326                                 case PH_DATA | CONFIRM:
1327                                 case DL_DATA | CONFIRM:
1328                                 break;
1329
1330                                 /* we receive audio data, we respond to it AND we send tones */
1331                                 case PH_DATA | INDICATION:
1332                                 case DL_DATA | INDICATION:
1333                                 case PH_CONTROL | INDICATION:
1334                                 i = 0;
1335                                 while(i < mISDNport->b_num)
1336                                 {
1337                                         if ((unsigned int)(mISDNport->b_addr[i]&STACK_ID_MASK) == (frm->addr&STACK_ID_MASK))
1338                                                 break;
1339                                         i++;
1340                                 }
1341                                 if (i == mISDNport->b_num)
1342                                 {
1343                                         PERROR("unhandled b-message (address 0x%x).\n", frm->addr);
1344                                         break;
1345                                 }
1346                                 if (mISDNport->b_port[i])
1347                                 {
1348 //PERROR("port sech: %s data\n", mISDNport->b_port[i]->p_name);
1349                                         mISDNport->b_port[i]->bchannel_receive(frm);
1350                                 } else
1351                                         PDEBUG(DEBUG_BCHANNEL, "b-channel is not associated to an ISDNPort (address 0x%x), ignoring.\n", frm->addr);
1352                                 break;
1353
1354                                 case PH_ACTIVATE | INDICATION:
1355                                 case DL_ESTABLISH | INDICATION:
1356                                 case PH_ACTIVATE | CONFIRM:
1357                                 case DL_ESTABLISH | CONFIRM:
1358                                 PDEBUG(DEBUG_BCHANNEL, "DL_ESTABLISH confirm: bchannel is now activated (address 0x%x).\n", frm->addr);
1359                                 i = 0;
1360                                 while(i < mISDNport->b_num)
1361                                 {
1362                                         if ((unsigned int)(mISDNport->b_addr[i]&STACK_ID_MASK) == (frm->addr&STACK_ID_MASK))
1363                                                 break;
1364                                         i++;
1365                                 }
1366                                 if (i == mISDNport->b_num)
1367                                 {
1368                                         PERROR("unhandled b-establish (address 0x%x).\n", frm->addr);
1369                                         break;
1370                                 }
1371                                 mISDNport->b_state[i] = B_STATE_ACTIVE;
1372                                 if (!mISDNport->b_port[i])
1373                                         bchannel_deactivate(mISDNport, i);
1374                                 else
1375                                         bchannel_activate(mISDNport, i);
1376                                 break;
1377
1378                                 case PH_DEACTIVATE | INDICATION:
1379                                 case DL_RELEASE | INDICATION:
1380                                 case PH_DEACTIVATE | CONFIRM:
1381                                 case DL_RELEASE | CONFIRM:
1382                                 PDEBUG(DEBUG_BCHANNEL, "DL_RELEASE confirm: bchannel is now de-activated (address 0x%x).\n", frm->addr);
1383                                 i = 0;
1384                                 while(i < mISDNport->b_num)
1385                                 {
1386                                         if ((unsigned int)(mISDNport->b_addr[i]&STACK_ID_MASK) == (frm->addr&STACK_ID_MASK))
1387                                                 break;
1388                                         i++;
1389                                 }
1390                                 if (i == mISDNport->b_num)
1391                                 {
1392                                         PERROR("unhandled b-release (address 0x%x).\n", frm->addr);
1393                                         break;
1394                                 }
1395                                 mISDNport->b_state[i] = B_STATE_IDLE;
1396                                 if (mISDNport->b_port[i])
1397                                         bchannel_activate(mISDNport, i);
1398                                 else
1399                                         bchannel_deactivate(mISDNport, i);
1400                                 break;
1401                         }
1402                         break;
1403                 }
1404
1405                 mISDNport = mISDNport->next;
1406         } 
1407         if (!mISDNport)
1408         {
1409                 if (frm->prim == (MGR_TIMER | INDICATION))
1410                         PERROR("unhandled timer indication message: prim(0x%x) addr(0x%x) msg->len(%d)\n", frm->prim, frm->addr, msg->len);
1411                 else
1412                         PERROR("unhandled message: prim(0x%x) addr(0x%x) msg->len(%d)\n", frm->prim, frm->addr, msg->len);
1413 //              PERROR("test: is_child: %x  of stack %x == %x (baddr %x frm %x)\n", (frm->addr&FLG_CHILD_STACK), ((unsigned int)(mISDNport_first->b_addr[0])&(~CHILD_ID_MASK)&STACK_ID_MASK), ((frm->addr)&(~CHILD_ID_MASK)&STACK_ID_MASK), mISDNport_first->b_addr[0], frm->addr);
1414         }
1415
1416         free_msg(msg);
1417         return(1);
1418 }
1419
1420
1421 /*
1422  * global function to add a new card (port)
1423  */
1424 struct mISDNport *mISDN_port_open(int port, int ptp, int ptmp)
1425 {
1426         int ret;
1427         unsigned char buff[1025];
1428         iframe_t *frm = (iframe_t *)buff;
1429         stack_info_t *stinf;
1430         struct mISDNport *mISDNport, **mISDNportp;
1431         int i, cnt;
1432         layer_info_t li;
1433 //      interface_info_t ii;
1434         net_stack_t *nst;
1435         manager_t *mgr;
1436         mISDN_pid_t pid;
1437         int pri = 0;
1438         int nt = 0;
1439         iframe_t dact;
1440
1441         /* open mISDNdevice if not already open */
1442         if (mISDNdevice < 0)
1443         {
1444                 ret = mISDN_open();
1445                 if (ret < 0)
1446                 {
1447                         PERROR("cannot open mISDN device ret=%d errno=%d (%s) Check for mISDN modules!\nAlso did you create \"/dev/mISDN\"? Do: \"mknod /dev/mISDN c 46 0\"\n", ret, errno, strerror(errno));
1448                         return(NULL);
1449                 }
1450                 mISDNdevice = ret;
1451                 PDEBUG(DEBUG_ISDN, "mISDN device opened.\n");
1452
1453                 /* create entity for layer 3 TE-mode */
1454                 mISDN_write_frame(mISDNdevice, buff, 0, MGR_NEWENTITY | REQUEST, 0, 0, NULL, TIMEOUT_1SEC);
1455                 ret = mISDN_read_frame(mISDNdevice, frm, sizeof(iframe_t), 0, MGR_NEWENTITY | CONFIRM, TIMEOUT_1SEC);
1456                 if (ret < (int)mISDN_HEADER_LEN)
1457                 {
1458                         noentity:
1459                         fprintf(stderr, "cannot request MGR_NEWENTITY from mISDN. Exitting due to software bug.");
1460                         exit(-1);
1461                 }
1462                 entity = frm->dinfo & 0xffff;
1463                 if (!entity)
1464                         goto noentity;
1465                 PDEBUG(DEBUG_ISDN, "our entity for l3-processes is %d.\n", entity);
1466         }
1467
1468         /* query port's requirements */
1469         cnt = mISDN_get_stack_count(mISDNdevice);
1470         if (cnt <= 0)
1471         {
1472                 PERROR("Found no card. Please be sure to load card drivers.\n");
1473                 return(NULL);
1474         }
1475         if (port>cnt || port<1)
1476         {
1477                 PERROR("Port (%d) given at 'ports' (options.conf) is out of existing port range (%d-%d)\n", port, 1, cnt);
1478                 return(NULL);
1479         }
1480         ret = mISDN_get_stack_info(mISDNdevice, port, buff, sizeof(buff));
1481         if (ret < 0)
1482         {
1483                 PERROR("Cannot get stack info for port %d (ret=%d)\n", port, ret);
1484                 return(NULL);
1485         }
1486         stinf = (stack_info_t *)&frm->data.p;
1487         switch(stinf->pid.protocol[0] & ~ISDN_PID_FEATURE_MASK)
1488         {
1489                 case ISDN_PID_L0_TE_S0:
1490                 PDEBUG(DEBUG_ISDN, "TE-mode BRI S/T interface line\n");
1491                 break;
1492                 case ISDN_PID_L0_NT_S0:
1493                 PDEBUG(DEBUG_ISDN, "NT-mode BRI S/T interface port\n");
1494                 nt = 1;
1495                 break;
1496                 case ISDN_PID_L0_TE_U:
1497                 PDEBUG(DEBUG_ISDN, "TE-mode BRI U   interface line\n");
1498                 break;
1499                 case ISDN_PID_L0_NT_U:
1500                 PDEBUG(DEBUG_ISDN, "NT-mode BRI U   interface port\n");
1501                 nt = 1;
1502                 break;
1503                 case ISDN_PID_L0_TE_UP2:
1504                 PDEBUG(DEBUG_ISDN, "TE-mode BRI Up2 interface line\n");
1505                 break;
1506                 case ISDN_PID_L0_NT_UP2:
1507                 PDEBUG(DEBUG_ISDN, "NT-mode BRI Up2 interface port\n");
1508                 nt = 1;
1509                 break;
1510                 case ISDN_PID_L0_TE_E1:
1511                 PDEBUG(DEBUG_ISDN, "TE-mode PRI E1  interface line\n");
1512                 pri = 1;
1513                 break;
1514                 case ISDN_PID_L0_NT_E1:
1515                 PDEBUG(DEBUG_ISDN, "LT-mode PRI E1  interface port\n");
1516                 pri = 1;
1517                 nt = 1;
1518                 break;
1519                 default:
1520                 PERROR("unknown port(%d) type 0x%08x\n", port, stinf->pid.protocol[0]);
1521                 return(NULL);
1522         }
1523         if (nt)
1524         {
1525                 /* NT */
1526                 if (stinf->pid.protocol[1] == 0)
1527                 {
1528                         PERROR("Given port %d: Missing layer 1 NT-mode protocol.\n", port);
1529                         return(NULL);
1530                 }
1531                 if (stinf->pid.protocol[2])
1532                 {
1533                         PERROR("Given port %d: Layer 2 protocol 0x%08x is detected, but not allowed for NT lib.\n", port, stinf->pid.protocol[2]);
1534                         return(NULL);
1535                 }
1536         } else
1537         {
1538                 /* TE */
1539                 if (stinf->pid.protocol[1] == 0)
1540                 {
1541                         PERROR("Given port %d: Missing layer 1 protocol.\n", port);
1542                         return(NULL);
1543                 }
1544                 if (stinf->pid.protocol[2] == 0)
1545                 {
1546                         PERROR("Given port %d: Missing layer 2 protocol.\n", port);
1547                         return(NULL);
1548                 }
1549                 if (stinf->pid.protocol[3] == 0)
1550                 {
1551                         PERROR("Given port %d: Missing layer 3 protocol.\n", port);
1552                         return(NULL);
1553                 } else
1554                 {
1555                         switch(stinf->pid.protocol[3] & ~ISDN_PID_FEATURE_MASK)
1556                         {
1557                                 case ISDN_PID_L3_DSS1USER:
1558                                 break;
1559
1560                                 default:
1561                                 PERROR("Given port %d: own protocol 0x%08x", port,stinf->pid.protocol[3]);
1562                                 return(NULL);
1563                         }
1564                 }
1565                 if (stinf->pid.protocol[4])
1566                 {
1567                         PERROR("Given port %d: Layer 4 protocol not allowed.\n", port);
1568                         return(NULL);
1569                 }
1570         }
1571
1572         /* add mISDNport structure */
1573         mISDNportp = &mISDNport_first;
1574         while(*mISDNportp)
1575                 mISDNportp = &mISDNport->next;
1576         mISDNport = (struct mISDNport *)calloc(1, sizeof(struct mISDNport));
1577         if (!mISDNport)
1578         {
1579                 PERROR("Cannot alloc mISDNport structure\n");
1580                 return(NULL);
1581         }
1582         pmemuse++;
1583         memset(mISDNport, 0, sizeof(mISDNport));
1584         *mISDNportp = mISDNport;
1585
1586         /* allocate ressources of port */
1587         msg_queue_init(&mISDNport->downqueue);
1588 //      SCPY(mISDNport->name, "noname");
1589         mISDNport->portnum = port;
1590         mISDNport->ntmode = nt;
1591         mISDNport->pri = pri;
1592         mISDNport->d_stid = stinf->id;
1593         PDEBUG(DEBUG_ISDN, "d_stid = 0x%x.\n", mISDNport->d_stid);
1594         mISDNport->b_num = stinf->childcnt;
1595         PDEBUG(DEBUG_ISDN, "Port has %d b-channels.\n", mISDNport->b_num);
1596         if ((stinf->pid.protocol[2]&ISDN_PID_L2_DF_PTP) || (nt&&ptp) || pri)
1597         {
1598                 PDEBUG(DEBUG_ISDN, "Port is point-to-point.\n");
1599                 mISDNport->ptp = ptp = 1;
1600                 if (ptmp && nt)
1601                 {
1602                         PDEBUG(DEBUG_ISDN, "Port is forced to point-to-multipoint.\n");
1603                         mISDNport->ptp = ptp = 0;
1604                 }
1605         }
1606         i = 0;
1607         while(i < stinf->childcnt)
1608         {
1609                 mISDNport->b_stid[i] = stinf->child[i];
1610                 PDEBUG(DEBUG_ISDN, "b_stid[%d] = 0x%x.\n", i, mISDNport->b_stid[i]);
1611                 i++;
1612         }
1613         memset(&li, 0, sizeof(li));
1614         UCPY(&li.name[0], (nt)?"net l2":"pbx l4");
1615         li.object_id = -1;
1616         li.extentions = 0;
1617         li.pid.protocol[nt?2:4] = (nt)?ISDN_PID_L2_LAPD_NET:ISDN_PID_L4_CAPI20;
1618         li.pid.layermask = ISDN_LAYER((nt?2:4));
1619         li.st = mISDNport->d_stid;
1620         ret = mISDN_new_layer(mISDNdevice, &li);
1621         if (ret)
1622         {
1623                 PERROR("Cannot add layer %d of port %d (ret %d)\n", nt?2:4, port, ret);
1624                 closeport:
1625                 mISDNport_close(mISDNport);
1626                 return(NULL);
1627         }
1628         mISDNport->upper_id = li.id;
1629         ret = mISDN_register_layer(mISDNdevice, mISDNport->d_stid, mISDNport->upper_id);
1630         if (ret)
1631         {
1632                 PERROR("Cannot register layer %d of port %d\n", nt?2:4, port);
1633                 goto closeport;
1634         }
1635         mISDNport->lower_id = mISDN_get_layerid(mISDNdevice, mISDNport->d_stid, nt?1:3); // id of lower layer (nt=1, te=3)
1636         if (mISDNport->lower_id < 0)
1637         {
1638                 PERROR("Cannot get layer(%d) id of port %d\n", nt?1:3, port);
1639                 goto closeport;
1640         }
1641         mISDNport->upper_id = mISDN_get_layerid(mISDNdevice, mISDNport->d_stid, nt?2:4); // id of uppermost layer (nt=2, te=4)
1642         if (mISDNport->upper_id < 0)
1643         {
1644                 PERROR("Cannot get layer(%d) id of port %d\n", nt?2:4, port);
1645                 goto closeport;
1646         }
1647         PDEBUG(DEBUG_ISDN, "Layer %d of port %d added.\n", nt?2:4, port);
1648
1649         /* if ntmode, establish L1 to send the tei removal during start */
1650         if (mISDNport->ntmode)
1651         {
1652                 iframe_t act;
1653                 /* L1 */
1654                 act.prim = PH_ACTIVATE | REQUEST; 
1655                 act.addr = mISDNport->upper_id | FLG_MSG_DOWN;
1656                 printf("UPPER ID 0x%x, addr 0x%x\n",mISDNport->upper_id, act.addr);
1657                 act.dinfo = 0;
1658                 act.len = 0;
1659                 mISDN_write(mISDNdevice, &act, mISDN_HEADER_LEN+act.len, TIMEOUT_1SEC);
1660                 usleep(10000); /* to be sure, that l1 is up */
1661         }
1662
1663         /* create nst (nt-mode only) */
1664         if (nt)
1665         {
1666                 mgr = &mISDNport->mgr;
1667                 nst = &mISDNport->nst;
1668
1669                 mgr->nst = nst;
1670                 nst->manager = mgr;
1671
1672                 nst->l3_manager = stack2manager_nt; /* messages from nt-mode */
1673                 nst->device = mISDNdevice;
1674                 nst->cardnr = port;
1675                 nst->d_stid = mISDNport->d_stid;
1676
1677                 nst->feature = FEATURE_NET_HOLD;
1678                 if (ptp)
1679                         nst->feature |= FEATURE_NET_PTP;
1680                 if (pri)
1681                         nst->feature |= FEATURE_NET_CRLEN2 | FEATURE_NET_EXTCID;
1682 #if 0
1683                 i = 0;
1684                 while(i < mISDNport->b_num)
1685                 {
1686                         nst->b_stid[i] = mISDNport->b_stid[i];
1687                         i++;
1688                 }
1689 #endif
1690                 nst->l1_id = mISDNport->lower_id;
1691                 nst->l2_id = mISDNport->upper_id;
1692
1693                 /* phd */       
1694                 msg_queue_init(&nst->down_queue);
1695
1696                 Isdnl2Init(nst);
1697                 Isdnl3Init(nst);
1698         }
1699
1700         /* if te-mode, query state link */
1701         if (!mISDNport->ntmode)
1702         {
1703                 iframe_t act;
1704                 /* L2 */
1705                 PDEBUG(DEBUG_ISDN, "sending short status request for port %d.\n", port);
1706                 act.prim = MGR_SHORTSTATUS | REQUEST; 
1707                 act.addr = mISDNport->upper_id | MSG_BROADCAST;
1708                 act.dinfo = SSTATUS_BROADCAST_BIT | SSTATUS_ALL;
1709                 act.len = 0;
1710                 mISDN_write(mISDNdevice, &act, mISDN_HEADER_LEN+act.len, TIMEOUT_1SEC);
1711         }
1712         /* if ptp AND te-mode, pull up the link */
1713         if (mISDNport->ptp && !mISDNport->ntmode)
1714         {
1715                 iframe_t act;
1716                 /* L2 */
1717                 act.prim = DL_ESTABLISH | REQUEST; 
1718                 act.addr = (mISDNport->upper_id & ~LAYER_ID_MASK) | 4 | FLG_MSG_DOWN;
1719                 act.dinfo = 0;
1720                 act.len = 0;
1721                 mISDN_write(mISDNdevice, &act, mISDN_HEADER_LEN+act.len, TIMEOUT_1SEC);
1722         }
1723         /* if ptp AND nt-mode, pull up the link */
1724         if (mISDNport->ptp && mISDNport->ntmode)
1725         {
1726                 msg_t *dmsg;
1727                 /* L2 */
1728                 dmsg = create_l2msg(DL_ESTABLISH | REQUEST, 0, 0);
1729                 if (mISDNport->nst.manager_l3(&mISDNport->nst, dmsg))
1730                         free_msg(dmsg);
1731         }
1732         /* initially, we assume that the link is down, exept for nt-ptmp */
1733         mISDNport->l2link = (mISDNport->ntmode && !mISDNport->ptp)?1:0;
1734
1735         PDEBUG(DEBUG_BCHANNEL, "using 'mISDN_dsp.o' module\n");
1736
1737         /* add all bchannel layers */
1738         i = 0;
1739         while(i < mISDNport->b_num)
1740         {
1741                 /* create new layer */
1742                 PDEBUG(DEBUG_BCHANNEL, "creating bchannel %d (index %d).\n" , i+1+(i>=15), i);
1743                 memset(&li, 0, sizeof(li));
1744                 memset(&pid, 0, sizeof(pid));
1745                 li.object_id = -1;
1746                 li.extentions = 0;
1747                 li.st = mISDNport->b_stid[i];
1748                 UCPY(li.name, "B L4");
1749                 li.pid.layermask = ISDN_LAYER((4));
1750                 li.pid.protocol[4] = ISDN_PID_L4_B_USER;
1751                 ret = mISDN_new_layer(mISDNdevice, &li);
1752                 if (ret)
1753                 {
1754                         failed_new_layer:
1755                         PERROR("mISDN_new_layer() failed to add bchannel %d (index %d)\n", i+1+(i>=15), i);
1756                         goto closeport;
1757                 }
1758                 mISDNport->b_addr[i] = li.id;
1759                 if (!li.id)
1760                 {
1761                         goto failed_new_layer;
1762                 }
1763                 PDEBUG(DEBUG_BCHANNEL, "new layer (b_addr=0x%x)\n", mISDNport->b_addr[i]);
1764
1765                 /* create new stack */
1766                 pid.protocol[1] = ISDN_PID_L1_B_64TRANS;
1767                 pid.protocol[2] = ISDN_PID_L2_B_TRANS;
1768                 pid.protocol[3] = ISDN_PID_L3_B_DSP;
1769                 pid.protocol[4] = ISDN_PID_L4_B_USER;
1770                 pid.layermask = ISDN_LAYER((1)) | ISDN_LAYER((2)) | ISDN_LAYER((3)) | ISDN_LAYER((4));
1771                 ret = mISDN_set_stack(mISDNdevice, mISDNport->b_stid[i], &pid);
1772                 if (ret)
1773                 {
1774                         stack_error:
1775                         PERROR("mISDN_set_stack() failed (ret=%d) to add bchannel (index %d) stid=0x%x\n", ret, i, mISDNport->b_stid[i]);
1776                         mISDN_write_frame(mISDNdevice, buff, mISDNport->b_addr[i], MGR_DELLAYER | REQUEST, 0, 0, NULL, TIMEOUT_1SEC);
1777                         mISDNport->b_addr[i] = 0;
1778 //                      mISDNport->b_addr_low[i] = 0;
1779                         goto closeport;
1780                 }
1781                 ret = mISDN_get_setstack_ind(mISDNdevice, mISDNport->b_addr[i]);
1782                 if (ret)
1783                         goto stack_error;
1784
1785                 /* get layer id */
1786                 mISDNport->b_addr[i] = mISDN_get_layerid(mISDNdevice, mISDNport->b_stid[i], 4);
1787                 if (!mISDNport->b_addr[i])
1788                         goto stack_error;
1789                 /* deactivate bchannel if already enabled due to crash */
1790                 PDEBUG(DEBUG_BCHANNEL, "deactivating bchannel (index %d) as a precaution.\n", i);
1791                 dact.prim = DL_RELEASE | REQUEST; 
1792                 dact.addr = mISDNport->b_addr[i] | FLG_MSG_DOWN;
1793                 dact.dinfo = 0;
1794                 dact.len = 0;
1795                 mISDN_write(mISDNdevice, &dact, mISDN_HEADER_LEN+dact.len, TIMEOUT_1SEC);
1796
1797                 i++;
1798         }
1799         PDEBUG(DEBUG_ISDN, "- port %d %s (%s) %d b-channels\n", mISDNport->portnum, (mISDNport->ntmode)?"NT-mode":"TE-mode", (mISDNport->ptp)?"Point-To-Point":"Multipoint", mISDNport->b_num);
1800         printlog("opening port %d %s (%s) %d b-channels\n", mISDNport->portnum, (mISDNport->ntmode)?"NT-mode":"TE-mode", (mISDNport->ptp)?"Point-To-Point":"Multipoint", mISDNport->b_num);
1801         return(mISDNport);
1802 }
1803
1804
1805 /*
1806  * function to free ALL cards (ports)
1807  */
1808 void mISDNport_close_all(void)
1809 {
1810         /* free all ports */
1811         while(mISDNport_first)
1812                 mISDNport_close(mISDNport_first);
1813 }
1814
1815 /*
1816  * free only one port
1817  */
1818 void mISDNport_close(struct mISDNport *mISDNport)
1819 {
1820         struct mISDNport **mISDNportp;
1821         class Port *port;
1822         classs PmISDN *pmISDN;
1823         net_stack_t *nst;
1824         unsigned char buf[32];
1825         int i;
1826
1827         /* remove all port instance that are linked to this mISDNport */
1828         port = port_first;
1829         while(port)
1830         {
1831                 if ((port->p_type&PORT_CLASS_MASK) == PORT_CLASS_mISDN)
1832                 {
1833                         pmISDN = (class PmISDN)*port;
1834                         if (pmISDN->p_m_mISDNport)
1835                         {
1836                                 PDEBUG(DEBUG_ISDN, "port %s uses mISDNport %d, destroying it.\n", pnISDN->p_name, mISDNport->portnum);
1837                                 delete pmISDN;
1838                         }
1839                 }
1840                 port = port->next;
1841         }
1842
1843         printlog("closing port %d\n", mISDNport->portnum);
1844
1845         /* free bchannels */
1846         i = 0;
1847         while(i < mISDNport->b_num)
1848         {
1849                 bchannel_deactivate(mISDNport, i);
1850                 PDEBUG(DEBUG_BCHANNEL, "freeing %s port %d bchannel (index %d).\n", (mISDNport->ntmode)?"NT":"TE", mISDNport->portnum, i);
1851                 if (mISDNport->b_stid[i])
1852                 {
1853                         mISDN_clear_stack(mISDNdevice, mISDNport->b_stid[i]);
1854                         if (mISDNport->b_addr[i])
1855                                 mISDN_write_frame(mISDNdevice, buf, mISDNport->b_addr[i] | FLG_MSG_DOWN, MGR_DELLAYER | REQUEST, 0, 0, NULL, TIMEOUT_1SEC);
1856                 }
1857                 i++;
1858         }
1859
1860         /* free ressources of port */
1861         msg_queue_purge(&mISDNport->downqueue);
1862
1863         /* free stacks */
1864         if (mISDNport->ntmode)
1865         {
1866                 nst = &mISDNport->nst;
1867                 if (nst->manager) /* to see if initialized */
1868                 {
1869                         PDEBUG(DEBUG_STACK, "the following messages are ok: one L3 process always exists (broadcast process) and some L2 instances (broadcast + current telephone's instances)\n");
1870                         cleanup_Isdnl3(nst);
1871                         cleanup_Isdnl2(nst);
1872
1873                         /* phd */
1874                         msg_queue_purge(&nst->down_queue);
1875                         if (nst->phd_down_msg)
1876                                 free(nst->phd_down_msg);
1877                 }
1878         }
1879
1880         PDEBUG(DEBUG_BCHANNEL, "freeing d-stack.\n");
1881         if (mISDNport->d_stid)
1882         {
1883 //              mISDN_clear_stack(mISDNdevice, mISDNport->d_stid);
1884                 if (mISDNport->lower_id)
1885                         mISDN_write_frame(mISDNdevice, buf, mISDNport->lower_id, MGR_DELLAYER | REQUEST, 0, 0, NULL, TIMEOUT_1SEC);
1886         }
1887
1888         /* remove from list */
1889         mISDNportp = &mISDNport_first;
1890         while(*mISDNportp)
1891         {
1892                 if (*mISDNportp == mISDNport)
1893                 {
1894                         *mISDNportp = (*mISDNportp)->next;
1895                         break;
1896                 }
1897                 mISDNportp = &((*mISDNportp)->next);
1898         }
1899
1900         if (!(*mISDNportp))
1901         {
1902                 PERROR("software error, mISDNport not in list\n");
1903                 exit(-1);
1904         }
1905         
1906         memset(mISDNport, 0, sizeof(struct mISDNport));
1907         free(mISDNport);
1908         pmemuse--;
1909
1910         /* close mISDNdevice, if no port */
1911         if (mISDNdevice>=0 && mISDNport_first==NULL)
1912         {
1913                 /* free entity */
1914                 mISDN_write_frame(mISDNdevice, buf, 0, MGR_DELENTITY | REQUEST, entity, 0, NULL, TIMEOUT_1SEC);
1915                 /* close device */
1916                 mISDN_close(mISDNdevice);
1917                 mISDNdevice = -1;
1918                 PDEBUG(DEBUG_ISDN, "mISDN device closed.\n");
1919         }
1920 }
1921
1922
1923 /*
1924  * global function to show all available isdn ports
1925  */
1926 void mISDN_port_info(void)
1927 {
1928         int err;
1929         int i, ii, p;
1930         int useable, nt, pri;
1931         unsigned char buff[1025];
1932         iframe_t *frm = (iframe_t *)buff;
1933         stack_info_t *stinf;
1934         int device;
1935
1936         /* open mISDN */
1937         if ((device = mISDN_open()) < 0)
1938         {
1939                 fprintf(stderr, "cannot open mISDN device ret=%d errno=%d (%s) Check for mISDN modules!\nAlso did you create \"/dev/mISDN\"? Do: \"mknod /dev/mISDN c 46 0\"\n", device, errno, strerror(errno));
1940                 exit(-1);
1941         }
1942
1943         /* get number of stacks */
1944         i = 1;
1945         ii = mISDN_get_stack_count(device);
1946         printf("\n");
1947         if (ii <= 0)
1948         {
1949                 printf("Found no card. Please be sure to load card drivers.\n");
1950         }
1951
1952         /* loop the number of cards and get their info */
1953         while(i <= ii)
1954         {
1955                 err = mISDN_get_stack_info(device, i, buff, sizeof(buff));
1956                 if (err <= 0)
1957                 {
1958                         fprintf(stderr, "mISDN_get_stack_info() failed: port=%d err=%d\n", i, err);
1959                         break;
1960                 }
1961                 stinf = (stack_info_t *)&frm->data.p;
1962
1963                 nt = pri = 0;
1964                 useable = 1;
1965
1966                 /* output the port info */
1967                 printf("Port %2d: ", i);
1968                 switch(stinf->pid.protocol[0] & ~ISDN_PID_FEATURE_MASK)
1969                 {
1970                         case ISDN_PID_L0_TE_S0:
1971                         printf("TE-mode BRI S/T interface line (for phone lines)");
1972 #if 0
1973                         if (stinf->pid.protocol[0] & ISDN_PID_L0_TE_S0_HFC & ISDN_PID_FEATURE_MASK)
1974                                 printf(" HFC multiport card");
1975 #endif
1976                         break;
1977                         case ISDN_PID_L0_NT_S0:
1978                         nt = 1;
1979                         printf("NT-mode BRI S/T interface port (for phones)");
1980 #if 0
1981                         if (stinf->pid.protocol[0] & ISDN_PID_L0_NT_S0_HFC & ISDN_PID_FEATURE_MASK)
1982                                 printf(" HFC multiport card");
1983 #endif
1984                         break;
1985                         case ISDN_PID_L0_TE_U:
1986                         printf("TE-mode BRI U   interface line");
1987                         break;
1988                         case ISDN_PID_L0_NT_U:
1989                         nt = 1;
1990                         printf("NT-mode BRI U   interface port");
1991                         break;
1992                         case ISDN_PID_L0_TE_UP2:
1993                         printf("TE-mode BRI Up2 interface line");
1994                         break;
1995                         case ISDN_PID_L0_NT_UP2:
1996                         nt = 1;
1997                         printf("NT-mode BRI Up2 interface port");
1998                         break;
1999                         case ISDN_PID_L0_TE_E1:
2000                         pri = 1;
2001                         printf("TE-mode PRI E1  interface line (for phone lines)");
2002 #if 0
2003                         if (stinf->pid.protocol[0] & ISDN_PID_L0_TE_E1_HFC & ISDN_PID_FEATURE_MASK)
2004                                 printf(" HFC-E1 card");
2005 #endif
2006                         break;
2007                         case ISDN_PID_L0_NT_E1:
2008                         nt = 1;
2009                         pri = 1;
2010                         printf("NT-mode PRI E1  interface port (for phones)");
2011 #if 0
2012                         if (stinf->pid.protocol[0] & ISDN_PID_L0_NT_E1_HFC & ISDN_PID_FEATURE_MASK)
2013                                 printf(" HFC-E1 card");
2014 #endif
2015                         break;
2016                         default:
2017                         useable = 0;
2018                         printf("unknown type 0x%08x",stinf->pid.protocol[0]);
2019                 }
2020                 printf("\n");
2021
2022                 if (nt)
2023                 {
2024                         if (stinf->pid.protocol[1] == 0)
2025                         {
2026                                 useable = 0;
2027                                 printf(" -> Missing layer 1 NT-mode protocol.\n");
2028                         }
2029                         p = 2;
2030                         while(p <= MAX_LAYER_NR) {
2031                                 if (stinf->pid.protocol[p])
2032                                 {
2033                                         useable = 0;
2034                                         printf(" -> Layer %d protocol 0x%08x is detected, but not allowed for NT lib.\n", p, stinf->pid.protocol[p]);
2035                                 }
2036                                 p++;
2037                         }
2038                         if (useable)
2039                         {
2040                                 if (pri)
2041                                         printf(" -> Interface is Point-To-Point (PRI).\n");
2042                                 else
2043                                         printf(" -> Interface can be Poin-To-Point/Multipoint.\n");
2044                         }
2045                 } else
2046                 {
2047                         if (stinf->pid.protocol[1] == 0)
2048                         {
2049                                 useable = 0;
2050                                 printf(" -> Missing layer 1 protocol.\n");
2051                         }
2052                         if (stinf->pid.protocol[2] == 0)
2053                         {
2054                                 useable = 0;
2055                                 printf(" -> Missing layer 2 protocol.\n");
2056                         }
2057                         if (stinf->pid.protocol[2] & ISDN_PID_L2_DF_PTP)
2058                         {
2059                                 printf(" -> Interface is Poin-To-Point.\n");
2060                         }
2061                         if (stinf->pid.protocol[3] == 0)
2062                         {
2063                                 useable = 0;
2064                                 printf(" -> Missing layer 3 protocol.\n");
2065                         } else
2066                         {
2067                                 printf(" -> Protocol: ");
2068                                 switch(stinf->pid.protocol[3] & ~ISDN_PID_FEATURE_MASK)
2069                                 {
2070                                         case ISDN_PID_L3_DSS1USER:
2071                                         printf("DSS1 (Euro ISDN)");
2072                                         break;
2073
2074                                         default:
2075                                         useable = 0;
2076                                         printf("unknown protocol 0x%08x",stinf->pid.protocol[3]);
2077                                 }
2078                                 printf("\n");
2079                         }
2080                         p = 4;
2081                         while(p <= MAX_LAYER_NR) {
2082                                 if (stinf->pid.protocol[p])
2083                                 {
2084                                         useable = 0;
2085                                         printf(" -> Layer %d protocol 0x%08x is detected, but not allowed for TE lib.\n", p, stinf->pid.protocol[p]);
2086                                 }
2087                                 p++;
2088                         }
2089                 }
2090                 printf("  - %d B-channels\n", stinf->childcnt);
2091
2092                 if (!useable)
2093                         printf(" * Port NOT useable for PBX\n");
2094
2095                 printf("--------\n");
2096
2097                 i++;
2098         }
2099         printf("\n");
2100
2101         /* close mISDN */
2102         if ((err = mISDN_close(device)))
2103         {
2104                 fprintf(stderr, "mISDN_close() failed: err=%d '%s'\n", err, strerror(err));
2105                 exit(-1);
2106         }
2107 }
2108
2109