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

📄 mscp_bbr.c

📁 <B>Digital的Unix操作系统VAX 4.2源码</B>
💻 C
📖 第 1 页 / 共 5 页
字号:
 * *   Outputs: * * *   Return	 *   Values:	EV_NULL */u_longmscp_bbr_step15( event, rp )    u_long			event;    register REQB		*rp;{    register BBRB		*bbrp = rp->connb->bbrb;    register UNITB		*up = rp->unitb;    register RCT_DESC		*sp;    u_long			prev_block;    u_long			prev_offset;    u_long			new_event;    Cprintf("mscp_bbr_step15: entered\n");    /* Calculate the offset of the new replacement descriptor and     * mark it as unallocated, with an LBN of 0.     */    sp = ( RCT_DESC * )bbrp->buf2 + ( bbrp->rbn % 128 );    sp->code = RCT_DS_UNALLOC;    sp->lbn = 0;    /* Calculate the LBN and offset of the previous replacement descriptor.     * Fill in the descriptor with the "unusable" descriptor code and a zero     * lbn.  If the previous descriptor is in a different RCT block from the     * current descriptor, multi-write the previous block into the RCT.     * If the descriptors are in the same block, redispatch to write that     * block immediately.     */    prev_block = ( bbrp->match_rbn / 128 ) + up->unt_size + 2;    prev_offset =  bbrp->match_rbn % 128;    if( prev_block != bbrp->cur_block ) {	sp = ( RCT_DESC * )bbrp->buf3 + prev_offset;	sp->lbn = bbrp->prev_desc.lbn;	sp->code = bbrp->prev_desc.code;	bbrp->multi_buf = bbrp->buf3;	rp->p1 = ( bbrp->match_rbn / 128 ) + up->unt_size + 2;	new_event = mscp_multi_write( rp );    } else {	sp = ( RCT_DESC * )bbrp->buf2 + prev_offset;	sp->lbn = bbrp->prev_desc.lbn;	sp->code = bbrp->prev_desc.code;	new_event = EV_BBRSUBSTEP;    }    return( new_event );}/**//* * *   Name:	mscp_bbr_step15a -  * *   Abstract:	This function writes the second "restored" RCT  *		block to the RCT. * *   Inputs:	IPL_SCS *		event			Event code *		rp			Request block pointer * *   Implicit *   Inputs:	 * *   Outputs: * * *   Return	 *   Values:	EV_NULL */u_longmscp_bbr_step15a( event, rp )    u_long			event;    register REQB		*rp;{    register BBRB		*bbrp = rp->connb->bbrb;    register UNITB		*up = rp->unitb;    u_long			new_event;    Cprintf("mscp_bbr_step15a: entered\n");    /* Multi-write the descriptor block back into the RCT.     */    bbrp->multi_buf = bbrp->buf2;    rp->p1 = ( bbrp->rbn / 128 ) + up->unt_size + 2;    new_event = mscp_multi_write( rp );    return( new_event );}/**//* * *   Name:	mscp_bbr_step16 -  * *   Abstract:	This function attempts to write the saved data back to *		the original LBN.  It also logs an error to the system *		error log if the RCT is full or corrupt. * *   Inputs:	IPL_SCS *		event			Event code *		rp			Request block pointer * *   Implicit *   Inputs:	 * *   Outputs: * * *   Return	 *   Values:	EV_NULL */u_longmscp_bbr_step16( event, rp )    u_long			event;    register REQB		*rp;{    register BBRB		*bbrp = rp->connb->bbrb;    register MSCP		*mp = rp->msgptr;    u_long			new_event, flags, subcode;    Cprintf("mscp_bbr_step16: entered\n");    flags = 0;    switch( event ) {    case EV_BBRRCTFULL:	bbrp->flags.bit.full = 1;	subcode = MSCP_SC_NORBL;	mscp_bbr_log(rp, MSLG_FM_DISK_TRN, flags, subcode);	break;    case EV_BBRINVRCT:	bbrp->flags.bit.corrupt = 1;	subcode = MSCP_SC_RCTBD;	mscp_bbr_log(rp, MSLG_FM_DISK_TRN, flags, subcode);	break;    default:	break;    }    rp->p1 = bbrp->lbn;    rp->p2 = 0;    if( bbrp->flags.bit.fe )	rp->p2 |= MSCP_MD_ERROR;    new_event = mscp_bbr_write( rp, bbrp->buf1 );    return( new_event );}/**//* * *   Name:	mscp_bbr_step17 - End of replacement update to RCT 0 * *   Abstract:	This function updates RCT sector 0 to reflect the  *		fact that replacement is no longer taking place. *		The sector, read in step 6, is modified and rewritten *		to the RCT.   * *   Inputs:	IPL_SCS *		event			Event code *		rp			Request block pointer * *   Implicit *   Inputs:	 * *   Outputs: * * *   Return	 *   Values:	EV_NULL */u_longmscp_bbr_step17( event, rp )    u_long			event;    register REQB		*rp;{    register BBRB		*bbrp = rp->connb->bbrb;    register UNITB		*up = rp->unitb;    register RCT_SECTOR_0	*sp = ( RCT_SECTOR_0 * )bbrp->buf0;    Cprintf("mscp_bbr_step17: entered\n");    /* Update RCT sector 0 by clearing the replacement flags, the lbn     * being replaced, the replacement block number, and the bad     * replacement block number.     */    sp->flags = 0;    sp->lbn = 0;    sp->rbn = 0;    sp->badrbn = 0;    /* Set up the buffer address and RCT sector 0 logical block      * number and start the multicopy write.     */    bbrp->multi_buf = bbrp->buf0;    rp->p1 = up->unt_size;    return( mscp_multi_write( rp ));}/**//* * *   Name:	mscp_bbr_step18 - Write protect the disk * *   Abstract:	This function logs the replacement attempt to the system *		error log and calls bbr_unlock() to restart the stalled *		I/O. * *   Inputs:	IPL_SCS *		event			Event code *		rp			Request block pointer * *   Implicit *   Inputs:	 * *   Outputs: * * *   Return	 *   Values:	EV_NULL */u_longmscp_bbr_step18( event, rp )    u_long			event;    register REQB		*rp;{    register MSCP		*mp = rp->msgptr;    register BBRB		*bbrp = rp->connb->bbrb;    register UNITB		*up = rp->unitb;    u_long			flags, subcode;    Cprintf("mscp_bbr_step18: entered\n");    subcode = 0;    flags = 0;    if(bbrp->flags.bit.full) {	subcode = MSCP_SC_RCTFL;	if(bbrp->flags.bit.match)	    flags = MSLG_LFR_BR;    }    else if(bbrp->flags.bit.mwfail) {	flags = MSLG_LFR_RI;	subcode = MSCP_SC_ICRCT;	if(bbrp->flags.bit.match)	    flags |= MSLG_LFR_BR;	if(bbrp->flags.bit.rplatt)	    flags |= MSLG_LFR_RP;    }    else if(bbrp->flags.bit.mrfail) {	flags = 0;	subcode = MSCP_SC_ICRCT;	if(bbrp->flags.bit.match)	    flags |= MSLG_LFR_BR;    }    else if(bbrp->flags.bit.corrupt) {	flags = MSLG_LFR_RI;	subcode = MSCP_SC_ICRCT;	if(bbrp->flags.bit.match)	    flags |= MSLG_LFR_BR;    }    else if(bbrp->flags.bit.recurs) {	subcode = MSCP_SC_RCTRC;	flags = (MSLG_LFR_BR | MSLG_LFR_RP);    }    else if(bbrp->flags.bit.repfail) {	flags = (MSLG_LFR_RP | MSLG_LFR_RF);	if(bbrp->flags.bit.match)	    flags |= MSLG_LFR_BR;	subcode = MSCP_SC_RPLFL;    }    mscp_bbr_log(rp, MSLG_FM_REPLACE, flags, subcode);    mscp_bbr_unlock(rp);    return( EV_NULL );}/**//* * *   Name:	mscp_rct_search -  * *   Abstract:	This function issues the multi-read for the RCT block *		which contains the primary RBN entry for the LBN we are *		replacing. * *   Inputs:	IPL_SCS *		event			Event code *		rp			Request block pointer * *   Implicit *   Inputs:	 * *   Outputs: * * *   Return	 *   Values:	EV_NULL */u_longmscp_rct_search( event, rp )    u_long			event;    register REQB		*rp;{    register UNITB		*up = rp->unitb;    register BBRB		*bbrp = rp->connb->bbrb;    Cprintf("mscp_rct_search: entered\n");    Push_bbr_state( ST_BB_RCTSEARCH );    bbrp->hash_rbn = ( bbrp->lbn / up->track ) * up->rbns;    bbrp->max_host_rbn = ((( up->unt_size - 1 ) / up->track ) + 1 ) * up->rbns;    bbrp->hash_block = ( bbrp->hash_rbn / 128 ) + up->unt_size + 2;    bbrp->hash_offset = bbrp->hash_rbn % 128;    bbrp->cur_block = bbrp->hash_block;    bbrp->cur_rbn = bbrp->hash_rbn;    bbrp->multi_buf = bbrp->buf2;    rp->p1 = bbrp->hash_block;    return( mscp_multi_read( rp ));}/**//* * *   Name:	mscp_rct_searcha -  * *   Abstract:	This function searchs the original hashed RCT block for *		a free RBN. * *   Inputs:	IPL_SCS *		event			Event code *		rp			Request block pointer * *   Implicit *   Inputs:	 * *   Outputs: * * *   Return	 *   Values:	EV_NULL */u_longmscp_rct_searcha( event, rp )    u_long			event;    REQB			*rp;{    register BBRB		*bbrp = rp->connb->bbrb;    register RCT_SECTOR_K	*sp = ( RCT_SECTOR_K * )bbrp->buf2;    register RCT_DESC		*descp;    register int		delta = 0;    register int		offset = bbrp->hash_offset;    register int		step;    u_long			new_event = EV_NULL;    Cprintf("mscp_rct_searcha: entered\n");    /* Search outward from the primary replacement block descriptor     * until an available descriptor is found or another terminating     * condition is seen:     *    descriptor block overflow or underflow,     *    end of the RCT,     *    or corrupted RCT.     */    while(( offset >= 0 ) &&	  ( offset < 128 ) &&	  ( new_event == EV_NULL ) &&	  ( !bbrp->flags.bit.eot )) {	descp = &sp->desc[offset];	new_event = mscp_test_descr( bbrp, descp );	delta = -delta;	if( delta >= 0 )	    delta++;	offset = bbrp->hash_offset + delta;	bbrp->cur_rbn = bbrp->hash_rbn + delta;    }    /* If block overflow or underflow occurred without finding an     * available descriptor or the end of the RCT, find the next     * unexamined descriptor, and do a linear search of the remainder     * of the block.     */    if( new_event == EV_NULL && !bbrp->flags.bit.eot ) {	delta = -delta;	if( delta >= 0 ) {	    delta++;	    step = 1;	} else	    step = -1;	offset = bbrp->hash_offset + delta;	bbrp->cur_rbn = bbrp->hash_rbn + delta;	while(( offset >= 0 ) &&	      ( offset < 128 ) &&	      ( new_event == EV_NULL ) &&	      ( !bbrp->flags.bit.eot )) {	    descp = &sp->desc[offset];	    new_event = mscp_test_descr( bbrp, descp );	    offset +=  step;	    bbrp->cur_rbn += step;	}    }    /* If an available descriptor has been found or the RCT is corrupted,     * pop the BBR state stack, and return status to the caller.     */    if( new_event != EV_NULL ) {	Pop_bbr_state();    /* No available descriptor has been found; continue     * processing in the next search substep.     */    } else	new_event = EV_BBRSUBSTEP;    return( new_event );   }/**//* * *   Name:	mscp_rct_searchb -  * *   Abstract:	This function searchs RCT blocks other than the original *		hashed block. * *   Inputs:	IPL_SCS *		event			Event code *		rp			Request block pointer * *   Implicit *   Inputs:	 * *   Outputs: * * *   Return	 *   Values:	EV_NULL */u_longmscp_rct_searchb( event, rp )    u_long			event;    register REQB		*rp;{    register BBRB		*bbrp = rp->connb->bbrb;    register RCT_DESC		*descp;    register RCT_SECTOR_K	*sp = ( RCT_SECTOR_K * )bbrp->buf2;    int				offset = 0;    u_long			new_event = EV_NULL;    Cprintf("mscp_rct_searchb: entered, Event = %x\n", event);    while( new_event == EV_NULL ) {	/* If first time through or end of RCT block, calculate the LBN of	 * the next RCT block to read.  If the end of the RCT has been seen,	 * wrap around to the beginning.  Calculate the RBN corresponding to	 * the start of the RCT block.  If the RBN is equal to the original	 * hashed primary descriptor RBN, the entire RCT has been searched	 * without encountering an available replacement block.  In this case,	 * return RCT full status; otherwise, read the new block and exit to	 * wait for the read to complete.	 */	if(( event == EV_BBRSUBSTEP ) || ( offset >= 128 )) {	    if( !bbrp->flags.bit.eot ) 		bbrp->cur_block++;	    else {		bbrp->cur_block = rp->unitb->unt_size + 2;		bbrp->flags.bit.eot = 0;	    }	    bbrp->cur_rbn =		128 * ( bbrp->cur_block - ( rp->unitb->unt_size + 2 ));	    if( bbrp->cur_rbn == bbrp->hash_rbn ) {		new_event = EV_BBRRCTFULL;	    } else {		bbrp->multi_buf = bbrp->buf2;		rp->p1 = bbrp->cur_block;		return( mscp_multi_read( rp ) );		break;	    }	/* The read completed.  Do a linear search of the RCT block, looking	 * for an available replacement block descriptor.  If the current	 * RBN matches the hashed primary descriptor RBN at any point in the	 * search, exit with RCT full status.	 */	} else {	    while(( offset < 128 ) &&		  ( new_event == EV_NULL ) &&		  ( !bbrp->flags.bit.eot )) {		descp = &sp->desc[offset];		new_event = mscp_test_descr( bbrp, descp );		offset++;		bbrp->cur_rbn++;		/* If bumped rbn equals start and previous RBN was not		 * free, then RCT is full.		 */		if( (bbrp->cur_rbn == bbrp->hash_rbn) && 				(new_event == EV_NULL) )		    new_event = EV_BBRRCTFULL;	    }	}    }    /* If the new_event is not null, the search has terminated.  Pop into     * the context of the caller before exiting.  If the new_event IS null,     * the multi-read is underway and will return to this routine when     * it completes.     */    if( new_event != EV_NULL )	Pop_bbr_state();        /* If at the end of the RCT then wrap to beginning     */    if( bbrp->flags.bit.eot )	new_event = EV_BBRSUBSTEP;    return( new_event );}/**//* * *   Name:	mscp_

⌨️ 快捷键说明

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