⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 isdn_lib.c

📁 Asterisk-1.4.4最新内核源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
			if (hold_bc) {				cb_log(4, stack->port, "REMOVEING Holder\n");				/*swap the backup to our new channel back*/				stack_holder_remove(stack, hold_bc);				memcpy(bc,hold_bc,sizeof(struct misdn_bchannel));				free(hold_bc);				bc->holded=0;			}					}						break;					case CC_SETUP|CONFIRM:		{			struct misdn_bchannel *bc=find_bc_by_l3id(stack, hh->dinfo);			int l3id = *((int *)(((u_char *)msg->data)+ mISDNUSER_HEAD_SIZE));			cb_log(4, stack->port, " --> lib: Event_ind:SETUP CONFIRM [NT] : new L3ID  is %x\n",l3id );				if (!bc) { cb_log(4, stack->port, "Bc Not found (after SETUP CONFIRM)\n"); return 0; }			cb_log (2,bc->port,"I IND :CC_SETUP|CONFIRM: old l3id:%x new l3id:%x\n", bc->l3_id, l3id);			bc->l3_id=l3id;			cb_event(EVENT_NEW_L3ID, bc, glob_mgr->user_data);		}		free_msg(msg);		return 0;      		case CC_SETUP|INDICATION:		{			struct misdn_bchannel* bc=misdn_lib_get_free_bc(stack->port, 0, 1, 0);			if (!bc) 			ERR_NO_CHANNEL:			{				msg_t *dmsg;				cb_log(4, stack->port, "Patch from MEIDANIS:Sending RELEASE_COMPLETE %x (No free Chan for you..)\n", hh->dinfo);				dmsg = create_l3msg(CC_RELEASE_COMPLETE | REQUEST,MT_RELEASE_COMPLETE, hh->dinfo,sizeof(RELEASE_COMPLETE_t), 1);				stack->nst.manager_l3(&stack->nst, dmsg);				free_msg(msg);				return 0;			}  			cb_log(7, stack->port, " --> new_process: New L3Id: %x\n",hh->dinfo);			bc->l3_id=hh->dinfo;		}		break;		case CC_CONNECT_ACKNOWLEDGE|INDICATION:#if 0		{			struct misdn_bchannel *bc=find_bc_by_l3id(stack, hh->dinfo);			if (bc) {				if ( !misdn_cap_is_speech(bc->capability)) {					int ret=setup_bc(bc);					if (ret == -EINVAL){						cb_log(0,bc->port,"send_event: setup_bc failed\n");											}				}			}		}#endif		break;				case CC_ALERTING|INDICATION:		case CC_PROCEEDING|INDICATION:		case CC_SETUP_ACKNOWLEDGE|INDICATION:			if(!stack->ptp) break;			case CC_CONNECT|INDICATION:		{#if 0			struct misdn_bchannel *bc=find_bc_by_l3id(stack, hh->dinfo);						if (!bc) {				msg_t *dmsg;				cb_log(0, stack->port,"!!!! We didn't found our bc, dinfo:%x on this port.\n",hh->dinfo);								cb_log(0, stack->port, "Releaseing call %x (No free Chan for you..)\n", hh->dinfo);				dmsg = create_l3msg(CC_RELEASE_COMPLETE | REQUEST,MT_RELEASE_COMPLETE, hh->dinfo,sizeof(RELEASE_COMPLETE_t), 1);				stack->nst.manager_l3(&stack->nst, dmsg);				free_msg(msg);				return 0;							}			int ret=setup_bc(bc);			if (ret == -EINVAL){				cb_log(0,bc->port,"handle_event_nt: setup_bc failed\n");				misdn_lib_send_event(bc,EVENT_RELEASE_COMPLETE);			}#endif		}		break;		case CC_DISCONNECT|INDICATION:		{			struct misdn_bchannel *bc=find_bc_by_l3id(stack, hh->dinfo);			if (!bc) {				bc=find_bc_by_masked_l3id(stack, hh->dinfo, 0xffff0000);				if (bc) { 					int myprocid=bc->l3_id&0x0000ffff;					hh->dinfo=(hh->dinfo&0xffff0000)|myprocid;					cb_log(3,stack->port,"Reject dinfo: %x cause:%d\n",hh->dinfo,bc->cause);					reject=1;						}			}		}		break;				case CC_FACILITY|INDICATION:		{			struct misdn_bchannel *bc=find_bc_by_l3id(stack, hh->dinfo);			if (!bc) {				bc=find_bc_by_masked_l3id(stack, hh->dinfo, 0xffff0000);				if (bc) { 					int myprocid=bc->l3_id&0x0000ffff;					hh->dinfo=(hh->dinfo&0xffff0000)|myprocid;					cb_log(4,bc->port,"Repaired reject Bug, new dinfo: %x\n",hh->dinfo);				}			}		}		break;				case CC_RELEASE_COMPLETE|INDICATION:			break;		case CC_SUSPEND|INDICATION:		{			msg_t *dmsg;			cb_log(4, stack->port, " --> Got Suspend, sending Reject for now\n");			dmsg = create_l3msg(CC_SUSPEND_REJECT | REQUEST,MT_SUSPEND_REJECT, hh->dinfo,sizeof(RELEASE_COMPLETE_t), 1);			stack->nst.manager_l3(&stack->nst, dmsg);			free_msg(msg);			return 0;		}		break;		case CC_RESUME|INDICATION:			break;		case CC_RELEASE|CONFIRM:			break;					case CC_RELEASE|INDICATION:			break;		case CC_RELEASE_CR|INDICATION:		{			struct misdn_bchannel *bc=find_bc_by_l3id(stack, hh->dinfo);			struct misdn_bchannel dummybc;			iframe_t frm; /* fake te frm to remove callref from global callreflist */			frm.dinfo = hh->dinfo;			frm.addr=stack->upper_id | FLG_MSG_DOWN;			frm.prim = CC_RELEASE_CR|INDICATION;			cb_log(4, stack->port, " --> Faking Realease_cr for %x\n",frm.addr);			/** removing procid **/			if (!bc) {				cb_log(4, stack->port, " --> Didn't found BC so temporarly creating dummy BC (l3id:%x) on this port.\n", hh->dinfo);				memset (&dummybc,0,sizeof(dummybc));				dummybc.port=stack->port;				dummybc.l3_id=hh->dinfo;				dummybc.nt=stack->nt;				bc=&dummybc; 			}				if (bc) {				if ( (bc->l3_id & 0xff00) == 0xff00) {					cb_log(4, stack->port, " --> Removing Process Id:%x on this port.\n", bc->l3_id&0xff);					stack->procids[bc->l3_id&0xff] = 0 ;				}			}			else cb_log(0, stack->port, "Couldnt find BC so I couldnt remove the Process!!!! this is a bad port.\n");				if (handle_cr(stack, &frm)<0) {			}			free_msg(msg);			return 0 ;		}		break;      		case CC_NEW_CR|INDICATION:			/*  Got New CR for bchan, for now I handle this one in */			/*  connect_ack, Need to be changed */		{			struct misdn_bchannel *bc=find_bc_by_l3id(stack, hh->dinfo);			int l3id = *((int *)(((u_char *)msg->data)+ mISDNUSER_HEAD_SIZE));			if (!bc) { cb_log(0, stack->port, " --> In NEW_CR: didn't found bc ??\n"); return -1;};			if (((l3id&0xff00)!=0xff00) && ((bc->l3_id&0xff00)==0xff00)) {				cb_log(4, stack->port, " --> Removing Process Id:%x on this port.\n", 0xff&bc->l3_id);				stack->procids[bc->l3_id&0xff] = 0 ;			}			cb_log(4, stack->port, "lib: Event_ind:CC_NEW_CR : very new L3ID  is %x\n",l3id );				bc->l3_id =l3id;			cb_event(EVENT_NEW_L3ID, bc, glob_mgr->user_data);				free_msg(msg);			return 0;		}      		case DL_ESTABLISH | INDICATION:		case DL_ESTABLISH | CONFIRM:		{			cb_log(3, stack->port, "%% GOT L2 Activate Info.\n");						if (stack->ptp && stack->l2link) {				cb_log(0, stack->port, "%% GOT L2 Activate Info. but we're activated already.. this l2 is faulty, blocking port\n");				cb_event(EVENT_PORT_ALARM, &stack->bc[0], glob_mgr->user_data);			}					/* when we get the L2 UP, the L1 is UP definitely too*/			stack->l1link = 1;			stack->l2link = 1;			stack->l2upcnt=0;						free_msg(msg);			return 0;		}		break;		case DL_RELEASE | INDICATION:		case DL_RELEASE | CONFIRM:		{			if (stack->ptp) {				cb_log(3 , stack->port, "%% GOT L2 DeActivate Info.\n");				if (stack->l2upcnt>3) {					cb_log(0 , stack->port, "!!! Could not Get the L2 up after 3 Attemps!!!\n");				}  else {#if 0					if (stack->nt) misdn_lib_reinit_nt_stack(stack->port);#endif					if (stack->l1link) {						misdn_lib_get_l2_up(stack);						stack->l2upcnt++;					}				}							} else 				cb_log(3, stack->port, "%% GOT L2 DeActivate Info.\n");						stack->l2link = 0;			free_msg(msg);			return 0;		}		break;		}	}		{		/*  Parse Events and fire_up to App. */		struct misdn_bchannel *bc;		struct misdn_bchannel dummybc;				enum event_e event = isdn_msg_get_event(msgs_g, msg, 1);    		bc=find_bc_by_l3id(stack, hh->dinfo);    		if (!bc) {      			cb_log(4, stack->port, " --> Didn't found BC so temporarly creating dummy BC (l3id:%x).\n", hh->dinfo);			memset (&dummybc,0,sizeof(dummybc));			dummybc.port=stack->port;			dummybc.l3_id=hh->dinfo;			dummybc.nt=stack->nt;			bc=&dummybc; 		}		if (bc ) {			isdn_msg_parse_event(msgs_g,msg,bc, 1);			switch (event) {				case EVENT_SETUP:					if (bc->channel<=0 || bc->channel==0xff) {						bc->channel=find_free_chan_in_stack(stack,bc, 0,0);						if (bc->channel<=0)							goto ERR_NO_CHANNEL;					} else if (!stack->ptp) 						cb_log(3,stack->port," --> PTMP but channel requested\n"); 					int ret=set_chan_in_stack(stack, bc->channel);					if (event==EVENT_SETUP && ret<0){						/* empty bchannel */						bc->channel=0;						bc->out_cause=44;						goto ERR_NO_CHANNEL;					} 					break;				case EVENT_RELEASE:				case EVENT_RELEASE_COMPLETE:					if (bc->channel>0)                        			empty_chan_in_stack(stack, bc->channel);					int tmpcause=bc->cause;				                empty_bc(bc);					bc->cause=tmpcause;					clean_up_bc(bc);					break;				default:				break;			}						if(!isdn_get_info(msgs_g,event,1)) {				cb_log(4, stack->port, "Unknown Event Ind: prim %x dinfo %x\n",hh->prim, hh->dinfo);			} else {				if (reject) {					switch(bc->cause){						case 17:							cb_log(1, stack->port, "Siemens Busy reject..\n");							break;						default:							break;					}				}				cb_event(event, bc, glob_mgr->user_data);			}      		} else {			cb_log(4, stack->port, "No BC found with l3id: prim %x dinfo %x\n",hh->prim, hh->dinfo);		}		free_msg(msg);	}	return 0;}static int handle_timers(msg_t* msg){	iframe_t *frm= (iframe_t*)msg->data;	struct misdn_stack *stack;   	/* Timer Stuff */	switch (frm->prim) {	case MGR_INITTIMER | CONFIRM:	case MGR_ADDTIMER | CONFIRM:	case MGR_DELTIMER | CONFIRM:	case MGR_REMOVETIMER | CONFIRM:		free_msg(msg);		return(1);	}      	if (frm->prim==(MGR_TIMER | INDICATION) ) {		for (stack = glob_mgr->stack_list;		     stack;		     stack = stack->next) {			itimer_t *it;      			if (!stack->nt) continue;      			it = stack->nst.tlist;			/* find timer */			for(it=stack->nst.tlist;			    it;			    it=it->next) {				if (it->id == (int)frm->addr)					break;			}			if (it) {				int ret;				ret = mISDN_write_frame(stack->midev, msg->data, frm->addr,							MGR_TIMER | RESPONSE, 0, 0, NULL, TIMEOUT_1SEC);				test_and_clear_bit(FLG_TIMER_RUNING, (long unsigned int *)&it->Flags);				ret = it->function(it->data);				free_msg(msg);				return 1;			}		}    		cb_log(0, 0, "Timer Msg without Timer ??\n");		free_msg(msg);		return 1;	}  	return 0;}void misdn_lib_tone_generator_start(struct misdn_bchannel *bc){	bc->generate_tone=1;}void misdn_lib_tone_generator_stop(struct misdn_bchannel *bc){	bc->generate_tone=0;}static int do_tone(struct misdn_bchannel *bc, int len){	bc->tone_cnt=len;		if (bc->generate_tone) {		cb_event(EVENT_TONE_GENERATE, bc, glob_mgr->user_data);				if ( !bc->nojitter ) {			misdn_tx_jitter(bc,len);		}				return 1;	}		return 0;}#ifdef MISDN_SAVE_DATAstatic void misdn_save_data(int id, char *p1, int l1, char *p2, int l2) {	char n1[32],n2[32];	sprintf(n1,"/tmp/misdn-rx-%d.raw",id);	sprintf(n2,"/tmp/misdn-tx-%d.raw",id);	FILE *rx=fopen(n1,"a+"); 	FILE *tx=fopen(n2,"a+");	if (!rx || !tx) {		cb_log(0,0,"Couldn't open files: %s\n",strerror(errno));		return ;	}		fwrite(p1,1,l1,rx);	fwrite(p2,1,l2,tx);		fclose(rx);	fclose(tx);}#endifvoid misdn_tx_jitter(struct misdn_bchannel *bc, int len){	char buf[4096 + mISDN_HEADER_LEN];	char *data=&buf[mISDN_HEADER_LEN];	iframe_t *txfrm= (iframe_t*)buf;	int jlen, r;		jlen=cb_jb_empty(bc,data,len);		if (jlen) {#ifdef MISDN_SAVE_DATA		misdn_save_data((bc->port*100+bc->channel), data, jlen, bc->bframe, bc->bframe_len);#endif		flip_buf_bits( data, jlen);				if (jlen < len) {			cb_log(7,bc->port,"Jitterbuffer Underrun.\n");		}				txfrm->prim = DL_DATA|REQUEST;				txfrm->dinfo = 0;				txfrm->addr = bc->addr|FLG_MSG_DOWN; /*  | IF_DOWN; */				txfrm->len =jlen;		cb_log(9, bc->port, "Transmitting %d samples 2 misdn\n", txfrm->len);		r=mISDN_write( glob_mgr->midev, buf, txfrm->len + mISDN_HEADER_LEN, 8000 );	} else {#define MISDN_GEN_SILENCE#ifdef MISDN_GEN_SILENCE		int cnt=len/TONE_SILENCE_SIZE;		int rest=len%TONE_SILENCE_SIZE;		int i;		for (i=0; i<cnt; i++) {			memcpy(data, tone_silence_flip, TONE_SILENCE_SIZE );			data +=TONE_SILENCE_SIZE;		}		if (rest) {			memcpy(data, tone_silence_flip, rest);		}		txfrm->prim = DL_DATA|REQUEST;		txfrm->dinfo = 0;		txfrm->addr = bc->addr|FLG_MSG_DOWN; /*  | IF_DOWN; */		txfrm->len =len;		cb_log(9, bc->port, "Transmitting %d samples 2 misdn\n", txfrm->len);		r=mISDN_write( glob_mgr->midev, buf, txfrm->len + mISDN_HEADER_LEN, 8000 );#endif	}}static int handle_bchan(msg_t *msg){	iframe_t *frm= (iframe_t*)msg->data;	struct misdn_bchannel *bc=find_bc_by_addr(frm->addr);		if (!bc) {		cb_log(1,0,"handle_bchan: BC not found for prim:%x with addr:%x dinfo:%x\n", frm->prim, frm->addr, frm->dinfo);		return 0 ;	}		struct misdn_stack *stack=get_stack_by_bc(bc);		if (!stack) {		cb_log(0, bc->port,"handle_bchan: STACK not found for prim:%x with addr:%x dinfo:%x\n", frm->prim, frm->addr, frm->dinfo);		return 0;	}		switch (frm->prim) {	case MGR_SETSTACK| CONFIRM:		cb_log(3, stack->port, "BCHAN: MGR_SETSTACK|CONFIRM pid:%d\n",bc->pid);		break;			case MGR_SETSTACK| INDICATION:		cb_log(3, stack->port, "BCHAN: MGR_SETSTACK|IND pid:%d\n",bc->pid);	break;#if 0	AGAIN:		bc->addr = mISDN_get_layerid(stack->midev, bc->b_stid, bc->layer);		if (!bc->addr) {			if (errno == EAGAIN) {				usleep(1000);				goto AGAIN;			}						cb_log(0,stack->port,"$$$ Get Layer (%d) Id Error: %s\n",bc->layer,strerror(errno));						/* we kill the channel later, when we received some			   data. */			bc->addr= frm->addr;		} else if ( bc->addr < 0) {			cb_log(0, stack->port,"$$$ bc->addr <0 Error:%s\n",strerror(errno));			bc->addr=0;		}				cb_log(4, stack->port," --> Got Adr %x\n", bc->addr);		free_msg(msg);					switch(bc->bc_state) {		case BCHAN_SETUP:			bc_state_change(bc,BCHAN_SETUPED);		break;		case BCHAN_CLEAN_REQUEST:		default:			cb_log(0, stack->port," --> STATE WASN'T SETUP (but %s) in SETSTACK|IND pid:%d\n",bc_state2str(bc->bc_state), bc->pid);			clean_up_bc(bc);		}		return 1;#endif	case MGR_DELLAYER| INDICATION:		cb_log(3, stack->port, "BCHAN: MGR_DELLAYER|IND pid:%d\n",bc->pid);		break;			case MGR_DELLAYER| CONFIRM:		cb_log(3, stack->port, "BCHAN: MGR_DELLAYER|CNF pid:%d\n",bc->pid);				bc->pid=0;		bc->addr=0;				free_msg(msg);		return 1;			case PH_ACTIVATE | INDICATION:	case DL_ESTABLISH | INDICATION:		cb_log(3, stack->port, "BCHAN: ACT Ind pid:%d\n", bc->pid);		free_msg(msg);		return 1;    	case PH_ACTIVATE | CONFIRM:	case DL_ESTABLISH | CONFIRM:				cb_log(3, stack->port, "BCHAN: bchan ACT Confirm pid:%d\n",bc->pid);		free_msg(msg);		

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -