-
- /* master stack */
- if (!(frm->addr&FLG_CHILD_STACK))
- {
- /* d-message */
- switch(frm->prim)
- {
- case MGR_SHORTSTATUS | INDICATION:
- case MGR_SHORTSTATUS | CONFIRM:
- switch(frm->dinfo) {
- case SSTATUS_L1_ACTIVATED:
- l1l2l3_trace_header(mISDNport, NULL, L1_ACTIVATE_REQ | (frm->prim & 0x3), DIRECTION_IN);
- end_trace();
- goto ss_act;
- case SSTATUS_L1_DEACTIVATED:
- l1l2l3_trace_header(mISDNport, NULL, L1_DEACTIVATE_REQ | (frm->prim & 0x3), DIRECTION_IN);
- end_trace();
- goto ss_deact;
- case SSTATUS_L2_ESTABLISHED:
- l1l2l3_trace_header(mISDNport, NULL, L2_ESTABLISH_REQ | (frm->prim & 0x3), DIRECTION_IN);
- end_trace();
- goto ss_estab;
- case SSTATUS_L2_RELEASED:
- l1l2l3_trace_header(mISDNport, NULL, L2_RELEASE_REQ | (frm->prim & 0x3), DIRECTION_IN);
- end_trace();
- goto ss_rel;
- }
- break;
-
- case PH_ACTIVATE | CONFIRM:
- case PH_ACTIVATE | INDICATION:
- l1l2l3_trace_header(mISDNport, NULL, L1_ACTIVATE_REQ | (frm->prim & 0x3), DIRECTION_IN);
- end_trace();
- if (mISDNport->ntmode)
- {
- mISDNport->l1link = 1;
- setup_queue(mISDNport, 1);
- goto l1_msg;
- }
- ss_act:
- mISDNport->l1link = 1;
- setup_queue(mISDNport, 1);
- break;
-
- case PH_DEACTIVATE | CONFIRM:
- case PH_DEACTIVATE | INDICATION:
- l1l2l3_trace_header(mISDNport, NULL, L1_DEACTIVATE_REQ | (frm->prim & 0x3), DIRECTION_IN);
- end_trace();
- if (mISDNport->ntmode)
- {
- mISDNport->l1link = 0;
- setup_queue(mISDNport, 0);
- goto l1_msg;
- }
- ss_deact:
- mISDNport->l1link = 0;
- setup_queue(mISDNport, 0);
- break;
-
- case PH_CONTROL | CONFIRM:
- case PH_CONTROL | INDICATION:
- PDEBUG(DEBUG_ISDN, "Received PH_CONTROL for port %d (%s).\n", mISDNport->portnum, mISDNport->ifport->interface->name);
- break;
-
- case DL_ESTABLISH | INDICATION:
- case DL_ESTABLISH | CONFIRM:
- l1l2l3_trace_header(mISDNport, NULL, DL_ESTABLISH_REQ | (frm->prim & 0x3), DIRECTION_IN);
- end_trace();
- if (!mISDNport->ntmode) break; /* !!!!!!!!!!!!!!!! */
- ss_estab:
- if (!mISDNport->ntmode || mISDNport->ptp)
- {
- if (mISDNport->l2establish)
- {
- mISDNport->l2establish = 0;
- PDEBUG(DEBUG_ISDN, "the link became active before l2establish timer expiry.\n");
- }
- mISDNport->l2link = 1;
- }
- break;
-
- case DL_RELEASE | INDICATION:
- case DL_RELEASE | CONFIRM:
- l1l2l3_trace_header(mISDNport, NULL, DL_RELEASE_REQ | (frm->prim & 0x3), DIRECTION_IN);
- end_trace();
- if (!mISDNport->ntmode) break; /* !!!!!!!!!!!!!!!! */
- ss_rel:
- if (!mISDNport->ntmode || mISDNport->ptp)
- {
- mISDNport->l2link = 0;
- if (mISDNport->l2hold)
- {
- time(&mISDNport->l2establish);
- PDEBUG(DEBUG_ISDN, "because we are ptp, we set a l2establish timer.\n");
- }
- }
- break;
-
- default:
- l1_msg:
- 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);
- if (frm->dinfo==(signed long)0xffffffff && frm->prim==(PH_DATA|CONFIRM))
- {
- PERROR("SERIOUS BUG, dinfo == 0xffffffff, prim == PH_DATA | CONFIRM !!!!\n");
- }
- /* d-message */
- if (mISDNport->ntmode)
- {
- /* l1-data enters the nt-mode library */
- nst = &mISDNport->nst;
- if (nst->l1_l2(nst, msg))
- free_msg(msg);
- return(1);
- } else
- {
- /* l3-data is sent to pbx */
- if (stack2manager_te(mISDNport, msg))
- free_msg(msg);
- return(1);
- }
- }
- } else
- /* child stack */
- {
- /* b-message */
- switch(frm->prim)
- {
- /* we don't care about confirms, we use rx data to sync tx */
- case PH_DATA | CONFIRM:
- case DL_DATA | CONFIRM:
- break;
-
- /* we receive audio data, we respond to it AND we send tones */
- case PH_DATA | INDICATION:
- case DL_DATA | INDICATION:
- case PH_CONTROL | INDICATION:
- case PH_SIGNAL | INDICATION:
- i = 0;
- while(i < mISDNport->b_num)
- {
- if ((unsigned int)(mISDNport->b_addr[i]&STACK_ID_MASK) == (frm->addr&STACK_ID_MASK))
- break;
- i++;
- }
- if (i == mISDNport->b_num)
- {
- PERROR("unhandled b-message (prim 0x%x address 0x%x).\n", frm->prim, frm->addr);
- break;
- }
- if (mISDNport->b_port[i])
- {
-//PERROR("port sech: %s data\n", mISDNport->b_port[i]->p_name);
- mISDNport->b_port[i]->bchannel_receive(frm);
- } else
- PDEBUG(DEBUG_BCHANNEL, "b-channel is not associated to an ISDNPort (address 0x%x), ignoring.\n", frm->addr);
- break;
-
- case PH_ACTIVATE | INDICATION:
- case DL_ESTABLISH | INDICATION:
- case PH_ACTIVATE | CONFIRM:
- case DL_ESTABLISH | CONFIRM:
- PDEBUG(DEBUG_BCHANNEL, "DL_ESTABLISH confirm: bchannel is now activated (address 0x%x).\n", frm->addr);
- i = 0;
- while(i < mISDNport->b_num)
- {
- if ((unsigned int)(mISDNport->b_addr[i]&STACK_ID_MASK) == (frm->addr&STACK_ID_MASK))
- break;
- i++;
- }
- if (i == mISDNport->b_num)
- {
- PERROR("unhandled b-establish (prim 0x%x address 0x%x).\n", frm->prim, frm->addr);
- break;
- }
- bchannel_event(mISDNport, i, B_EVENT_ACTIVATED);
- break;
-
- case PH_DEACTIVATE | INDICATION:
- case DL_RELEASE | INDICATION:
- case PH_DEACTIVATE | CONFIRM:
- case DL_RELEASE | CONFIRM:
- PDEBUG(DEBUG_BCHANNEL, "DL_RELEASE confirm: bchannel is now de-activated (address 0x%x).\n", frm->addr);
- i = 0;
- while(i < mISDNport->b_num)
- {
- if ((unsigned int)(mISDNport->b_addr[i]&STACK_ID_MASK) == (frm->addr&STACK_ID_MASK))
- break;
- i++;
- }
- if (i == mISDNport->b_num)
- {
- PERROR("unhandled b-release (prim 0x%x address 0x%x).\n", frm->prim, frm->addr);
- break;
- }
- bchannel_event(mISDNport, i, B_EVENT_DEACTIVATED);
- break;
-
- default:
- PERROR("child message not handled: prim(0x%x) addr(0x%x) msg->len(%d)\n", frm->prim, frm->addr, msg->len);
- }
- }
-
- out:
- free_msg(msg);
- return(1);
-}
-#endif
-
-#ifdef SOCKET_MISDN
-int do_layer3(struct mlayer3 *ml3, unsigned int cmd, unsigned int pid, struct l3_msg *l3m)
-{
- /* IMPORTAINT:
- *
- * l3m must be queued, except for MT_ASSIGN
- *
- */
- struct mISDNport *mISDNport = (struct mISDNport *)ml3->priv;
- struct mbuffer *mb;
-
- /* special MT_ASSIGN handling:
- *
- * if we request a PID from mlayer, we always do it while lcr is locked.
- * therefore we must check the MT_ASSIGN reply first before we lock.
- * this is because the MT_ASSIGN reply is received with the requesting
- * process, not by the mlayer thread!
- * this means, that the reply is sent during call of the request.
- * we must check if we get a reply and we know that we lcr is currently
- * locked.
- */
- if (cmd == MT_ASSIGN)
- {
- /* let's do some checking if someone changes stack behaviour */
- if (mt_assign_pid != 0)
- FATAL("someone played with the mISDNuser stack. MT_ASSIGN not currently expected.\n");
- if ((pid >> 16) != MISDN_CES_MASTER)
- FATAL("someone played with the mISDNuser stack. MT_ASSIGN is expected with master CES.\n");
- mt_assign_pid = pid;
- return(0);
- }
-
- /* queue message, create, if required */
- if (!l3m)
- {
- l3m = alloc_l3_msg();
- if (!l3m)
- FATAL("No memory for layer 3 message\n");
- }
- mb = container_of(l3m, struct mbuffer, l3);
- l3m->type = cmd;
- l3m->pid = pid;
- mqueue_tail(&mISDNport->upqueue, mb);
- return 0;
-}
-
-#endif
-
-
-/*
- * global function to add a new card (port)
- */
-struct mISDNport *mISDNport_open(int port, int ptp, int force_nt, int l2hold, struct interface *interface)
-{
- int ret;
- struct mISDNport *mISDNport, **mISDNportp;
- int i, cnt;
- int pri, bri, pots;
- int nt, te;
-#ifdef SOCKET_MISDN
-// struct mlayer3 *ml3;
- struct mISDN_devinfo devinfo;
- unsigned int protocol, prop;
-
- ret = ioctl(mISDNsocket, IMGETCOUNT, &cnt);
- if (ret < 0)
- {
- fprintf(stderr, "Cannot get number of mISDN devices. (ioctl IMGETCOUNT failed ret=%d)\n", ret);
- return(NULL);
- }
-#else
- unsigned char buff[1025];
- iframe_t *frm = (iframe_t *)buff;
-// interface_info_t ii;
- net_stack_t *nst;
- manager_t *mgr;
- layer_info_t li;
- stack_info_t *stinf;
-
- /* query port's requirements */
- cnt = mISDN_get_stack_count(mISDNdevice);
-#endif
-
- if (cnt <= 0)
- {
- PERROR_RUNTIME("Found no card. Please be sure to load card drivers.\n");
- return(NULL);
- }
- if (port>cnt || port<1)
- {
- PERROR_RUNTIME("Port (%d) given at 'ports' (options.conf) is out of existing port range (%d-%d)\n", port, 1, cnt);
- return(NULL);
- }
-
- pri = bri = pots = nt = te = 0;
-#ifdef SOCKET_MISDN
- devinfo.id = port - 1;
- ret = ioctl(mISDNsocket, IMGETDEVINFO, &devinfo);
- if (ret <= 0)
- {
- PERROR_RUNTIME("Cannot get device information for port %d. (ioctl IMGETDEVINFO failed ret=%d)\n", i, ret);
- return(NULL);
- }
- /* output the port info */
- if (devinfo.Dprotocols & (1 << ISDN_P_TE_S0))
- {
- bri = 1;
- te = 1;
- }
- if (devinfo.Dprotocols & (1 << ISDN_P_NT_S0))