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

📄 x100p-ss7.c

📁 OpenSS7 This the fourth public release of the OpenSS7 Master Package. See README in the release for
💻 C
📖 第 1 页 / 共 5 页
字号:
		sl_rc_stop(q, xp);		ctrace(sl_txc_send_sios(q, xp));		sl_poc_stop(q, xp);	/* ok if not ITUT */		xp->sl.statem.emergency = 0;		xp->sl.statem.local_processor_outage = 0;		xp->sl.statem.remote_processor_outage = 0;	/* ok if not ANSI */		xp->sl.statem.lsc_state = SL_STATE_OUT_OF_SERVICE;	}	return (QR_DONE);}STATIC INLINE voidsl_txc_send_sib(queue_t *q, struct xp *xp){	xp->sl.statem.tx.sio = LSSU_SIB;	xp->sl.statem.lssu_available = 1;}STATIC INLINE voidsl_txc_send_sipo(queue_t *q, struct xp *xp){	xp_timer_stop(xp, t7);	if (xp->option.pvar == SS7_PVAR_ANSI_92)		xp_timer_stop(xp, t6);	xp->sl.statem.tx.sio = LSSU_SIPO;	xp->sl.statem.lssu_available = 1;}STATIC INLINE voidsl_txc_send_sio(queue_t *q, struct xp *xp){	xp->sl.statem.tx.sio = LSSU_SIO;	xp->sl.statem.lssu_available = 1;}STATIC INLINE voidsl_txc_send_sin(queue_t *q, struct xp *xp){	xp->sl.statem.tx.sio = LSSU_SIN;	xp->sl.statem.lssu_available = 1;}STATIC INLINE voidsl_txc_send_sie(queue_t *q, struct xp *xp){	xp->sl.statem.tx.sio = LSSU_SIE;	xp->sl.statem.lssu_available = 1;}STATIC INLINE voidsl_txc_send_msu(queue_t *q, struct xp *xp){	if (xp->sl.rtb.q_count)		xp_timer_start(xp, t7);	xp->sl.statem.msu_inhibited = 0;	xp->sl.statem.lssu_available = 0;}STATIC INLINE voidsl_txc_send_fisu(queue_t *q, struct xp *xp){	xp_timer_stop(xp, t7);	if (xp->option.pvar == SS7_PVAR_ANSI_92 && !(xp->option.popt & SS7_POPT_PCR))		xp_timer_stop(xp, t6);	xp->sl.statem.msu_inhibited = 1;	xp->sl.statem.lssu_available = 0;}STATIC INLINE voidsl_txc_fsnx_value(queue_t *q, struct xp *xp){	if (xp->sl.statem.tx.X.fsn != xp->sl.statem.rx.X.fsn)		xp->sl.statem.tx.X.fsn = xp->sl.statem.rx.X.fsn;}STATIC INLINE voidsl_txc_nack_to_be_sent(queue_t *q, struct xp *xp){	xp->sl.statem.tx.N.bib = xp->sl.statem.tx.N.bib ? 0 : xp->sl.statem.ib_mask;}STATIC INLINE intsl_lsc_rtb_cleared(queue_t *q, struct xp *xp){	int err;	if (xp->sl.statem.lsc_state == SL_STATE_PROCESSOR_OUTAGE) {		xp->sl.statem.remote_processor_outage = 0;		if (xp->sl.statem.local_processor_outage)			return (QR_DONE);		if ((err = sl_remote_processor_recovered_ind(q, xp)))			return (err);		if ((err = sl_rtb_cleared_ind(q, xp)))			return (err);		sl_txc_send_msu(q, xp);		xp->sl.statem.lsc_state = SL_STATE_IN_SERVICE;	}	return (QR_DONE);}STATIC void sl_check_congestion(queue_t *q, struct xp *xp);STATIC INLINE voidsl_txc_bsnr_and_bibr(queue_t *q, struct xp *xp){	int pcr = xp->option.popt & SS7_POPT_PCR;	xp->sl.statem.tx.R.bsn = xp->sl.statem.rx.R.bsn;	xp->sl.statem.tx.R.bib = xp->sl.statem.rx.R.bib;	if (xp->sl.statem.clear_rtb) {		bufq_purge(&xp->sl.rtb);		xp->sl.statem.Ct = 0;		sl_check_congestion(q, xp);		xp->sl.statem.tx.F.fsn = (xp->sl.statem.tx.R.bsn + 1) & xp->sl.statem.sn_mask;		xp->sl.statem.tx.L.fsn = xp->sl.statem.tx.R.bsn;		xp->sl.statem.tx.N.fsn = xp->sl.statem.tx.R.bsn;		xp->sl.statem.tx.N.fib = xp->sl.statem.tx.R.bib;		xp->sl.statem.Z = (xp->sl.statem.tx.R.bsn + 1) & xp->sl.statem.sn_mask;		xp->sl.statem.z_ptr = NULL;		/* FIXME: handle error return */		sl_lsc_rtb_cleared(q, xp);		xp->sl.statem.clear_rtb = 0;		xp->sl.statem.rtb_full = 0;		return;	}	if (xp->sl.statem.tx.F.fsn != ((xp->sl.statem.tx.R.bsn + 1) & xp->sl.statem.sn_mask)) {		if (xp->sl.statem.sib_received) {			xp->sl.statem.sib_received = 0;			xp_timer_stop(xp, t6);		}		do {			freemsg(bufq_dequeue(&xp->sl.rtb));			xp->sl.statem.Ct--;			xp->sl.statem.tx.F.fsn =			    (xp->sl.statem.tx.F.fsn + 1) & xp->sl.statem.sn_mask;		} while (xp->sl.statem.tx.F.fsn !=			 ((xp->sl.statem.tx.R.bsn + 1) & xp->sl.statem.sn_mask));		sl_check_congestion(q, xp);		if (xp->sl.rtb.q_count == 0) {			xp_timer_stop(xp, t7);		} else {			xp_timer_start(xp, t7);		}		if (!pcr		    || (xp->sl.rtb.q_msgs < xp->sl.config.N1			&& xp->sl.rtb.q_count < xp->sl.config.N2))			xp->sl.statem.rtb_full = 0;		if (SN_OUTSIDE(xp->sl.statem.tx.F.fsn, xp->sl.statem.Z, xp->sl.statem.tx.L.fsn)		    || !xp->sl.rtb.q_count) {			xp->sl.statem.Z = xp->sl.statem.tx.F.fsn;			xp->sl.statem.z_ptr = xp->sl.rtb.q_head;		}	}	if (pcr)		return;	if (xp->sl.statem.tx.N.fib != xp->sl.statem.tx.R.bib) {		if (xp->sl.statem.sib_received) {			xp->sl.statem.sib_received = 0;			xp_timer_stop(xp, t6);		}		xp->sl.statem.tx.N.fib = xp->sl.statem.tx.R.bib;		xp->sl.statem.tx.N.fsn = (xp->sl.statem.tx.F.fsn - 1) & xp->sl.statem.sn_mask;		if ((xp->sl.statem.z_ptr = xp->sl.rtb.q_head) != NULL)			xp->sl.statem.retrans_cycle = 1;		return;	}}STATIC INLINE voidsl_txc_sib_received(queue_t *q, struct xp *xp){	/* FIXME: consider these variations for all */	if (xp->option.pvar == SS7_PVAR_ANSI_92 && xp->sl.statem.lssu_available)		if (xp->sl.statem.tx.sio != LSSU_SIB)			return;	if (xp->option.pvar != SS7_PVAR_ITUT_93 && !xp->sl.rtb.q_count)		return;	if (!xp->sl.statem.sib_received) {		xp_timer_start(xp, t6);		xp->sl.statem.sib_received = 1;	}	xp_timer_start(xp, t7);}STATIC INLINE voidsl_txc_clear_rtb(queue_t *q, struct xp *xp){	bufq_purge(&xp->sl.rtb);	xp->sl.statem.Ct = 0;	xp->sl.statem.clear_rtb = 1;	xp->sl.statem.rtb_full = 0;	/* added */	/* FIXME: should probably follow more of the ITUT flush_buffers stuff like reseting Z and	   FSNF, FSNL, FSNT. */	sl_check_congestion(q, xp);}STATIC INLINE voidsl_txc_clear_tb(queue_t *q, struct xp *xp){	bufq_purge(&xp->sl.tb);	flushq(xp->iq, FLUSHDATA);	xp->sl.statem.Cm = 0;	sl_check_congestion(q, xp);}STATIC INLINE voidsl_txc_flush_buffers(queue_t *q, struct xp *xp){	bufq_purge(&xp->sl.rtb);	xp->sl.statem.rtb_full = 0;	xp->sl.statem.Ct = 0;	bufq_purge(&xp->sl.tb);	flushq(xp->iq, FLUSHDATA);	xp->sl.statem.Cm = 0;	xp->sl.statem.Z = 0;	xp->sl.statem.z_ptr = NULL;	/* Z =0 error in ITUT 93 and ANSI */	xp->sl.statem.Z = xp->sl.statem.tx.F.fsn =	    (xp->sl.statem.tx.R.bsn + 1) & xp->sl.statem.sn_mask;	xp->sl.statem.tx.L.fsn = xp->sl.statem.rx.R.bsn;	xp->sl.statem.rx.T.fsn = xp->sl.statem.rx.R.bsn;	xp_timer_stop(xp, t7);	return;}STATIC INLINE voidsl_rc_fsnt_value(queue_t *q, struct xp *xp){	xp->sl.statem.rx.T.fsn = xp->sl.statem.tx.N.fsn;}STATIC INLINE intsl_txc_retrieval_request_and_fsnc(queue_t *q, struct xp *xp, sl_ulong fsnc){	mblk_t *mp;	int err;	xp->sl.statem.tx.C.fsn = fsnc & (xp->sl.statem.sn_mask);	/* 	 *  FIXME: Q.704/5.7.2 states:	 *	 *  5.7.2   If a changeover order or acknowledgement containing an unreasonable value of the forward	 *  sequence number is received, no buffer updating or retrieval is performed, and new traffic is started	 *  on the alternative signalling link(s).	 *	 *  It will be necessary to check FSNC for "reasonableness" here and flush RTB and TB and return	 *  retrieval-complete indication with a return code of "unreasonable FSNC".	 *	 *  (Tell the SIGTRAN working group and M2UA guys about this!)	 */	while (xp->sl.rtb.q_count && xp->sl.statem.tx.F.fsn != ((fsnc + 1) & xp->sl.statem.sn_mask)) {		freemsg(bufq_dequeue(&xp->sl.rtb));		xp->sl.statem.Ct--;		xp->sl.statem.tx.F.fsn = (xp->sl.statem.tx.F.fsn + 1) & xp->sl.statem.sn_mask;	}	while ((mp = bufq_dequeue(&xp->sl.tb))) {		xp->sl.statem.Cm--;		bufq_queue(&xp->sl.rtb, mp);		xp->sl.statem.Ct++;		if (!xp->sl.statem.Cm)			qenable(xp->iq);	}	xp->sl.statem.Z = xp->sl.statem.tx.F.fsn =	    (xp->sl.statem.tx.C.fsn + 1) & xp->sl.statem.sn_mask;	while ((mp = bufq_dequeue(&xp->sl.rtb))) {		xp->sl.statem.Ct--;		if ((err = sl_retrieved_message_ind(q, xp, mp)))			return (err);	}	xp->sl.statem.rtb_full = 0;	if ((err = sl_retrieval_complete_ind(q, xp)))		return (err);	xp->sl.statem.Cm = 0;	xp->sl.statem.Ct = 0;	xp->sl.statem.tx.N.fsn = xp->sl.statem.tx.L.fsn = xp->sl.statem.tx.C.fsn;	return (QR_DONE);}STATIC INLINE voidsl_daedt_fisu(queue_t *q, struct xp *xp, mblk_t *mp){	if (xp->option.popt & SS7_POPT_XSN) {		*(sl_ushort *) mp->b_wptr =		    htons(xp->sl.statem.tx.N.bsn | xp->sl.statem.tx.N.bib);		mp->b_wptr += sizeof(sl_ushort);		*(sl_ushort *) mp->b_wptr =		    htons(xp->sl.statem.tx.N.fsn | xp->sl.statem.tx.N.fib);		mp->b_wptr += sizeof(sl_ushort);		*(sl_ushort *) mp->b_wptr = 0;		mp->b_wptr += sizeof(sl_ushort);	} else {		*(sl_uchar *) mp->b_wptr = (xp->sl.statem.tx.N.bsn | xp->sl.statem.tx.N.bib);		mp->b_wptr += sizeof(sl_uchar);		*(sl_uchar *) mp->b_wptr = (xp->sl.statem.tx.N.fsn | xp->sl.statem.tx.N.fib);		mp->b_wptr += sizeof(sl_uchar);		*(sl_uchar *) mp->b_wptr = 0;		mp->b_wptr += sizeof(sl_uchar);	}}STATIC INLINE voidsl_daedt_lssu(queue_t *q, struct xp *xp, mblk_t *mp){	if (xp->option.popt & SS7_POPT_XSN) {		*(sl_ushort *) mp->b_wptr =		    htons(xp->sl.statem.tx.N.bsn | xp->sl.statem.tx.N.bib);		mp->b_wptr += sizeof(sl_ushort);		*(sl_ushort *) mp->b_wptr =		    htons(xp->sl.statem.tx.N.fsn | xp->sl.statem.tx.N.fib);		mp->b_wptr += sizeof(sl_ushort);		*(sl_ushort *) mp->b_wptr = htons(1);		mp->b_wptr += sizeof(sl_ushort);	} else {		*(sl_uchar *) mp->b_wptr = (xp->sl.statem.tx.N.bsn | xp->sl.statem.tx.N.bib);		mp->b_wptr += sizeof(sl_uchar);		*(sl_uchar *) mp->b_wptr = (xp->sl.statem.tx.N.fsn | xp->sl.statem.tx.N.fib);		mp->b_wptr += sizeof(sl_uchar);		*(sl_uchar *) mp->b_wptr = 1;		mp->b_wptr += sizeof(sl_uchar);	}	*(sl_uchar *) mp->b_wptr = (xp->sl.statem.tx.sio);	mp->b_wptr += sizeof(sl_uchar);}STATIC INLINE voidsl_daedt_msu(queue_t *q, struct xp *xp, mblk_t *mp){	int len = msgdsize(mp);	if (xp->option.popt & SS7_POPT_XSN) {		((sl_ushort *) mp->b_rptr)[0] =		    htons(xp->sl.statem.tx.N.bsn | xp->sl.statem.tx.N.bib);		((sl_ushort *) mp->b_rptr)[1] =		    htons(xp->sl.statem.tx.N.fsn | xp->sl.statem.tx.N.fib);		((sl_ushort *) mp->b_rptr)[2] = htons(len - 6 < 512 ? len - 6 : 511);	} else {		((sl_uchar *) mp->b_rptr)[0] = (xp->sl.statem.tx.N.bsn | xp->sl.statem.tx.N.bib);		((sl_uchar *) mp->b_rptr)[1] = (xp->sl.statem.tx.N.fsn | xp->sl.statem.tx.N.fib);		((sl_uchar *) mp->b_rptr)[2] = (len - 3 < 64 ? len - 3 : 63);	}}STATIC INLINE mblk_t *sl_txc_transmission_request(queue_t *q, struct xp *xp){	mblk_t *mp = NULL;	int pcr;	if (xp->sl.statem.txc_state != SL_STATE_IN_SERVICE)		return (mp);	pcr = xp->option.popt & SS7_POPT_PCR;	if (xp->sl.statem.lssu_available) {		if ((mp = ss7_fast_allocb(&xp_bufpool, 7, BPRI_HI))) {			if (xp->sl.statem.tx.sio == LSSU_SIB)				xp->sl.statem.lssu_available = 0;			xp->sl.statem.tx.N.fsn = xp->sl.statem.tx.L.fsn;			xp->sl.statem.tx.N.bib = xp->sl.statem.tx.N.bib;			xp->sl.statem.tx.N.bsn =			    (xp->sl.statem.tx.X.fsn - 1) & xp->sl.statem.sn_mask;			xp->sl.statem.tx.N.fib = xp->sl.statem.tx.N.fib;			sl_daedt_lssu(q, xp, mp);		}		return (mp);	}	if (xp->sl.statem.msu_inhibited) {		if ((mp = ss7_fast_allocb(&xp_bufpool, 6, BPRI_HI))) {			xp->sl.statem.tx.N.fsn = xp->sl.statem.tx.L.fsn;			xp->sl.statem.tx.N.bib = xp->sl.statem.tx.N.bib;			xp->sl.statem.tx.N.bsn =			    (xp->sl.statem.tx.X.fsn - 1) & xp->sl.statem.sn_mask;			xp->sl.statem.tx.N.fib = xp->sl.statem.tx.N.fib;			sl_daedt_fisu(q, xp, mp);		}		return (mp);	}	if (pcr) {		if ((xp->sl.rtb.q_msgs < xp->sl.config.N1)		    && (xp->sl.rtb.q_count < xp->sl.config.N2)) {			xp->sl.statem.forced_retransmission = 0;			xp->sl.statem.rtb_full = 0;		}		if (xp->sl.tb.q_count && xp->sl.statem.rtb_full) {			xp->sl.statem.forced_retransmission = 1;		}	}	if ((!pcr && xp->sl.statem.retrans_cycle)	    || (pcr		&& (xp->sl.statem.forced_retransmission		    || (!xp->sl.tb.q_count && xp->sl.rtb.q_count)))) {		mblk_t *bp;		if ((bp = xp->sl.statem.z_ptr) && !(mp = dupmsg(bp)))			return (mp);		if (!bp && pcr) {			if ((bp = xp->sl.statem.z_ptr = xp->sl.rtb.q_head) && !(mp = dupmsg(bp)))				return (mp);			xp->sl.statem.Z = xp->sl.statem.tx.F.fsn;		}		if (mp) {			xp->sl.statem.z_ptr = bp->b_next;			if (pcr) {				xp->sl.statem.tx.N.fsn = xp->sl.statem.Z;				xp->sl.statem.tx.N.fib = xp->sl.statem.tx.N.fib;				xp->sl.statem.tx.N.bsn =				    (xp->sl.statem.tx.X.fsn - 1) & xp->sl.statem.sn_mask;				xp->sl.statem.tx.N.bib = xp->sl.statem.tx.N.bib;				xp->sl.statem.Z = (xp->sl.statem.Z + 1) & xp->sl.statem.sn_mask;			} else {				xp->sl.statem.tx.N.fsn =				    (xp->sl.statem.tx.N.fsn + 1) & xp->sl.statem.sn_mask;				xp->sl.statem.tx.N.fib = xp->sl.statem.tx.N.fib;				xp->sl.statem.tx.N.bsn =				    (xp->sl.statem.tx.X.fsn - 1) & xp->sl.statem.sn_mask;				xp->sl.statem.tx.N.bib = xp->sl.statem.tx.N.bib;			}			sl_daedt_msu(q, xp, mp);			if (xp->sl.statem.tx.N.fsn == xp->sl.statem.tx.L.fsn			    || xp->sl.statem.z_ptr == NULL)				xp->sl.statem.retrans_cycle = 0;		}		return (mp);	}	if ((!pcr && (!xp->sl.tb.q_count || xp->sl.statem.rtb_full))	    || (pcr && (!xp->sl.tb.q_count && !xp->sl.rtb.q_count))) {		if ((mp = ss7_fast_allocb(&xp_bufpool, 6, BPRI_HI))) {			xp->sl.statem.tx.N.fsn = xp->sl.statem.tx.L.fsn;			xp->sl.statem.tx.N.bib = xp->sl.statem.tx.N.bib;			xp->sl.statem.tx.N.bsn =			    (xp->sl.statem.tx.X.fsn - 1) & xp->sl.statem.sn_mask;			xp->sl.statem.tx.N.fib = xp->sl.statem.tx.N.fib;			sl_daedt_fisu(q, xp, mp);		}		return (mp);	} else {		spin_lock(&xp->sl.tb.q_lock);		if ((mp = bufq_head(&xp->sl.tb)) && (mp = dupmsg(mp))) {			mblk_t *bp = bufq_dequeue(&xp->sl.tb);			xp->sl.statem.Cm--;			if (!xp->sl.statem.Cm)				qenable(xp->iq);			xp->sl.statem.tx.L.fsn =			    (xp->sl.statem.tx.L.fsn + 1) & xp->sl.statem.sn_mask;			xp->sl.statem.tx.N.fsn = xp->sl.statem.tx.L.fsn;			if (!xp->sl.rtb.q_count)				xp_timer_start(xp, t7);			bufq_queue(&xp->sl.rtb, bp);			xp->sl.statem.Ct++;			sl_rc_fsnt_value(q, xp);			if (pcr) {				if ((xp->sl.rtb.q_msgs >= xp->sl.config.N1)				    || (xp->sl.rtb.q_count >= xp->sl.config.N2)) {					xp->sl.statem.rtb_full = 1;					xp->sl.statem.forced_retransmission = 1;				}			} else {				if ((xp->sl.rtb.q_msgs >= xp->sl.config.N1)				    || (xp->sl.rtb.q_count >= xp->sl.config.N2)				    || (xp->sl.statem.tx.L.fsn ==					((xp->sl.statem.tx.F.fsn - 2) & xp->sl.statem.sn_mask)))					xp->sl.statem.rtb_full = 1;			}			xp->sl.statem.tx.N.bib = xp->sl.statem.tx.N.bib;			xp->sl.statem.tx.N.bsn =			    (xp->sl.statem.tx.X.fsn - 1) & xp->sl.statem.sn_mask;			xp->sl.statem.tx.N.fib = xp->sl.statem.tx.N.fib;			sl_daedt_msu(q, xp, mp);		}		spin_unlock(&xp->sl.tb.q_lock);		return (mp);	}}STATIC INLINE voidsl_daedr_start(queue_t *q, struct xp *xp){	xp->sdt.statem.daedr_state = SDT_STATE_IN_SERVICE;	xp->sdl.statem.rx_state = SDL_STATE_IN_SERVICE;	xp->sdl.config.ifflags |= (SDL_IF_UP | SDL_IF_RX_RUNNING);}STATIC INLINE voidsl_rc_start(queue_t *q, struct xp *xp){	if (xp->sl.statem.rc_state == SL_STATE_IDLE) {		xp->sl.statem.rx.X.fsn = 0;		xp->sl.statem.rx.X.fib = xp->sl.statem.ib_mask;		xp->sl.statem.rx.F.fsn = 0;		xp->sl.statem.rx.T.fsn = xp->sl.statem.sn_mask;		xp->sl.statem.rtr = 0;	/* Basic only (note 1). */		if (xp->option.pvar == SS7_PVAR_ANSI_92)			xp->sl.statem.msu_fisu_accepted = 1;		else			xp->sl.statem.msu_fisu_accepted = 0;		xp->sl.statem.abnormal_bsnr = 0;		xp->sl.statem.abnormal_fibr = 0;	/* Basic only (note 1). */		xp->sl.statem.congestion_discard = 0;		xp->sl.statem.congestion_accept = 0;		sl_daedr_start(q, xp);		xp->sl.statem.rc_state = SL_STATE_IN_SERVICE;		return;		/* 		 *   Note 1 - Although rtr and abnormal_fibr are only applicable to the Basic procedure (and		 *   not PCR), these state machine variables are never examined by PCR routines, so PCR and		 *   basic can share the same start procedures.		 */	}}STATIC INLINE voidsl_rc_reject_msu_fisu(queue_t *q, struct xp *xp)

⌨️ 快捷键说明

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