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

📄 msi_isr.c

📁 <B>Digital的Unix操作系统VAX 4.2源码</B>
💻 C
📖 第 1 页 / 共 2 页
字号:
			}			break;		    case ID:			Rcheck_id( pccb, Siibp, msibp, event )			if( Msibp ) {			    Rformat_msib( Siibp, Msibp )			    Insert_msib( Msibp, rdoneq )			}			break;		    case IDREQ:			Rcheck_idreq( pccb, Siibp, msibp, event )			if( Msibp ) {			    Rqueue_id( pccb, Msibp, Siibp )			    start_xfp = 1;			}			break;		    case RST:		    case STRT:			break;		    case CNF:		    case RETDAT:			event = SE_INVOPCODE;			break;		    default:			event = SE_UNKOPCODE;		}	    }	    if( event ) {		Rproc_error( pccb, Siibp, msibp, event, lpc, rdoneq )		event = 0;		if( lpc ) {		    Unlock_rfp( pccb )		    ( void )splx( save_ipl );		    return;		}	    }	} else {	    if( Rinvalid_srcaddr( pccb, Siibp )) {		Rlog_invsrcaddr( pccb, Siibp )	    }	}	Rreset_cmdblk( Siibp )	if( rfree == NULL ) {	    rfree = siibp;	}    }    /*     */    if( rfree ) {	if( rfree != ( siibp = pccb->Rbusy )) {	    Term_thread( siibp )	    Thread_cmdblk( rfree, rfree )	    if( *pccb->Msitlp == 0 ) {		*pccb->Msitlp = (( SIIBUF * )rfree )->cmdblkaddr;	    }	} else {	    *pccb->Msitlp = (( SIIBUF * )rfree )->cmdblkaddr;	}    }    /*     */    {    register msibq	*qaddr = &rdoneq;    Unlock_rfp( pccb )    if( start_xfp ) {	Xstart_xfp( pccb )    }    for( msibp = qaddr->flink; msibp != qaddr; msibp = qaddr->flink ) {	Remove_msib( Msibp )	Rfinish_receive( pccb, Msibp )    }    }    ( void )splx( save_ipl );}/*   Name:	msi_xfp		- MSI Transmit Fork Process Routine * *   Abstract:	 * *   Inputs: * *   IPL_SCS			- Interrupt processor level *   pccb			- Port Command and Control Block pointer *	pd.msi			-  MSI specific PCCB fields *	    lpstatus.xfork	-   1 * *   Outputs: * *   IPL_SCS			- Interrupt processor level *   pccb			- Port Command and Control Block pointer *	pd.msi			-  MSI specific PCCB fields *	    comqh		-   MSIB high priority command queue *	    comql		-   MSIB low priority command queue *	    dfreeq		-   MSIB datagram free queue *	    lpcinfo		-   Optional local port crash information *		pkth		-    Address of MSI packet *		pktsize		-    Size of msi packet *		pport_addr	-    Packet remote port station address *	    lpstatus.timer	-   Retry delay timer active flag *	    lpstatus.xfork	-   0 *	    mfreeq		-   MSIB message free queue *	    perport		-   Per-DSSI port information *		rpstatus.dip	-    Transmit delaying in progress flag *		rpstatus.path	-    Path exists flag *		xretrys		-    Current transmit retry attempt *		xretryq		-    MSIB transmit retry queue *		xretry_timer	-    Transmit retry timer( in 10 msecs ) *		xseqno		-    Next transmit sequence number *	    siiregptrs		-   MSI register pointers *		msidscr		-    DSSI control register *		msiilp		-    Initiator list pointer register *	    xbusy		-   First transmit-in-progress SIIBUF pointer *	    xdmap		-   Transmit Fork Process DMapping Buffer Info *	    xfree		-   First free transmit SIIBUF pointer * *   SMP:	PCCB:	Interlock Access *			Prevent PB deletion *		XFP:	Interlock Access *			Guarantee only one active XFP and XFP_TIMER threads *			Prohibits Port Crashing *			Prohibits VC closure except at behalf this routine *		DFREEQ:	Interlock Access *		MFREEQ:	Interlock Access *		COMQH:	Interlock Access *		COMQL:	Interlock Access */voidmsi_xfp( pccb )    register PCCB		*pccb;{    msibq			xmsg_doneq;    register siibq		*siibp,				*xstart_xmt = NULL;    register msibq		*msibp;    register MSI_PPORTINFO	*dpi;    u_long			save_ipl;/* */    Xfp_started( pccb, save_ipl )    Init_queue( xmsg_doneq )    /*     */    while(( Msibp = (( SIIBUF * )( siibp = pccb->Xbusy ))->save_msib )) {	if( Siibp->cmdblk.status == ST_SUCCESS ) {	    if( *pccb->Msiilp != Siibp->cmdblkaddr ) {		dpi = &pccb->Perport[ Siibp->cmdblk.dst ];		Xtransmit_done( pccb, Msibp, dpi, xmsg_doneq )		Xfree_siib( pccb, Siibp )	    } else {		break;	    }	} else if( Xsii_busy( pccb )) {	    break;	} else {	    /* Delay for awhile, if not we get bad status and cause 	       duplicate packets to be resent. We should not have to 	       do this, UGH SII. */	    DELAY( 2 );	    if( Siibp->cmdblk.status == ST_SUCCESS ) {		continue;	    } else if( Xfalse_nack( pccb, Siibp )) {		Siibp->cmdblk.status = ST_SUCCESS;		continue;	    } else if( *pccb->Msiilp ) {		*pccb->Msiilp = 0;		dpi = &pccb->Perport[ Siibp->cmdblk.dst ];		if( Xignore_xmtfail( pccb, Siibp, dpi )) {		    Xdiscard_msib( pccb, Msibp )		    Xfree_siib( pccb, Siibp )		} else {		    Xretry_xmt( pccb, siibp, msibp, dpi, xmsg_doneq )		}	    }	    if((( SIIBUF * )( siibp = pccb->Xbusy ))->save_msib ) {		xstart_xmt = siibp;		Xreset_xbusy( pccb, siibp )	    }	    break;	}    }    if( Siibp->save_msib == 0 || xstart_xmt ) {	siibp = pccb->Xfree;	Thread_cmdblk( siibp, siibp )    }    /*     */    while((( SIIBUF * )( siibp = pccb->Xfree ))->save_msib == 0 ) {	Remove_comqh( pccb, msibp )	if( Msibp == NULL ) {	    Remove_comql( pccb, msibp )	    if( Msibp == NULL ) {		break;	    }	}	dpi = &pccb->Perport[ Msibp->Rport_addr ];	if( Rpstatus_dip( dpi )) {	    Xinsert_xretryq( dpi, Msibp )	} else if( Xabort_xmt( dpi, Msibp )) {	    Xdiscard_msib( pccb, Msibp )	} else {	    Xformat_siib( Siibp, Msibp )	    if( Msibp->Ph.opcode == RETDAT ) {		u_long	event = 0;		Xcheck_lretdat( pccb, Msibp, event )		if( event == 0 ) {		    ( void )bcopy( pccb->Xdmap.Saddr,				   Siibp->Xpkt.retdat.data,				   pccb->Xdmap.ssize );		    if( Lp_msih( Msibp->Ph )) {			Set_lp( Siibp->Xpkt.ph )		    }		    Msibp->Framelength += U_short( pccb->Xdmap.ssize );		} else {		    Xretdat_error( pccb, msibp, event, xmsg_doneq )		    Unlock_xfp( pccb )		    ( void )splx( save_ipl );		    return;		}	    }	    if( Vc_msib( Msibp )) {		Xset_xseqno( dpi, Siibp )	    }	    Siibp->save_msib = Msibp;	    Xformat_cmdblk( pccb, Siibp, Msibp )	    Xformat_xlink( Siibp, Msibp )	    if( xstart_xmt == NULL ) {		xstart_xmt = siibp;	    }	    pccb->Xfree = siibp->flink;	}    }    /*     */    if( xstart_xmt ) {	Interrupt_enable( xstart_xmt )	siibp = pccb->Xfree;	Term_thread( siibp )	siibp = siibp->blink;	Interrupt_enable( Siibp )	if( *pccb->Msiilp == 0 ) {	    *pccb->Msiilp = (( SIIBUF * )xstart_xmt )->cmdblkaddr;	    *pccb->Msidscr = MSIDSCR_SOUT;	}	if( xstart_xmt != pccb->Xbusy ) {	    Thread_cmdblk( xstart_xmt, xstart_xmt )	}    }    /*     */    Unlock_xfp( pccb )    while(( msibp = xmsg_doneq.flink ) != &xmsg_doneq ) {	Remove_msib( Msibp )	( void )scs_msg_snt( pccb,			     ( SCSH * )Msibp->Msg.text,			     ( Msibp->Framelength - MSG_OVHD ));    }    ( void )splx( save_ipl );}/*   Name:	msi_xfp_timer	- MSI Transmit Fork Process Timer Routine * *   Abstract:	 * *   Inputs: * *   IPL_SCS		- Interrupt processor level *   pccb			- Port Command and Control Block pointer *	pd.msi			-  MSI specific PCCB fields *	    lpstatus.timer	-   1 * *   Outputs: * *   IPL_SCS		- Interrupt processor level *   pccb			- Port Command and Control Block pointer *	pd.msi			-  MSI specific PCCB fields *	    comqh		-   MSIB high priority command queue *	    lpstatus.timer	-   Retry delay timer status bit *	    lpstatus.xfork	-   Transmit Fork Process scheduled flag *	    perport		-   Per-DSSI port information *		rpstatus.dip	-    Transmit delaying in progress flag *		xretryq		-    MSIB transmit retry queue *		xretry_timer	-    Transmit retry timer( in 10 msecs ) *	    xforkb		-   Transmit Fork Process fork block * *   SMP:	XFP:	Interlock Access *			Guarantee only one active XFP and XFP_TIMER threads *			Prohibits Port Crashing *			Prohibits VC closure except at behalf this routine *		COMQH:	Interlock Access *		PCCB:	Interlock Access */voidmsi_xfp_timer( pccb )    register PCCB		*pccb;{    u_long			save_ipl;    register msibq		*msibp;    register MSI_PPORTINFO	*ppi;    register u_long		portnum,				reschedule = 0,				start_xfp = 0;    /*     */    Xfp_timer_started( pccb, save_ipl )    for( portnum = 0; portnum < MSI_MAXNUM_PORT; ++portnum ) {	ppi = &pccb->Perport[ portnum ];	if( Rpstatus_dip( ppi )) {	    if( --ppi->xretry_timer ) {		reschedule = 1;	    } else {		Clear_rpdip( ppi )		while(( msibp = ppi->xretryq.flink ) != &ppi->xretryq ) {		    Remove_msib( Msibp )		    Insert_comqh( pccb, Msibp )		    start_xfp = 1;		}	    }	}    }    if( reschedule ) {	Xstart_xfp_timer( pccb )    }    Unlock_xfp( pccb )    if( start_xfp ) {	Xstart_xfp( pccb )    }    ( void )splx( save_ipl );}

⌨️ 快捷键说明

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