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

📄 rf_map.c

📁 RAIDFrame是个非常好的磁盘阵列RAID仿真工具
💻 C
📖 第 1 页 / 共 3 页
字号:
	t_pda = pdaList;	pdaList = pdaList->next;	bzero((char *)t_pda, sizeof(RF_PhysDiskAddr_t));	pda_p = asm_p->parityInfo = t_pda;	pda_p->type = RF_PDA_TYPE_PARITY;	(layoutPtr->map->MapParity)(raidPtr, rf_RaidAddressOfPrevStripeUnitBoundary(layoutPtr, startAddrWithinStripe),				    &(pda_p->row), &(pda_p->col), &(pda_p->startSector), remap);	pda_p->numSector = layoutPtr->sectorsPerStripeUnit;	/* raidAddr may be needed to find unit to redirect to */	pda_p->raidAddress = rf_RaidAddressOfPrevStripeUnitBoundary(layoutPtr, startAddrWithinStripe);	rf_ASMCheckStatus(raidPtr,pda_p,asm_p,disks,1);	rf_ASMParityAdjust(asm_p->parityInfo,startAddrWithinStripe,endAddress,layoutPtr,asm_p);	break;      case 2: /* two fault tolerant */	RF_ASSERT(pdaList && pdaList->next);	t_pda = pdaList;	pdaList = pdaList->next;	bzero((char *)t_pda, sizeof(RF_PhysDiskAddr_t));	pda_p = asm_p->parityInfo = t_pda;	pda_p->type = RF_PDA_TYPE_PARITY;	t_pda = pdaList;	pdaList = pdaList->next;	bzero((char *)t_pda, sizeof(RF_PhysDiskAddr_t));	pda_q = asm_p->qInfo = t_pda;	pda_q->type = RF_PDA_TYPE_Q;	(layoutPtr->map->MapParity)(raidPtr, rf_RaidAddressOfPrevStripeUnitBoundary(layoutPtr, startAddrWithinStripe),				    &(pda_p->row), &(pda_p->col), &(pda_p->startSector), remap);	(layoutPtr->map->MapQ)(raidPtr, rf_RaidAddressOfPrevStripeUnitBoundary(layoutPtr, startAddrWithinStripe),			       &(pda_q->row), &(pda_q->col), &(pda_q->startSector), remap);	pda_q->numSector = pda_p->numSector = layoutPtr->sectorsPerStripeUnit;	/* raidAddr may be needed to find unit to redirect to */	pda_p->raidAddress = rf_RaidAddressOfPrevStripeUnitBoundary(layoutPtr, startAddrWithinStripe);	pda_q->raidAddress = rf_RaidAddressOfPrevStripeUnitBoundary(layoutPtr, startAddrWithinStripe);	/* failure mode stuff */	rf_ASMCheckStatus(raidPtr,pda_p,asm_p,disks,1);	rf_ASMCheckStatus(raidPtr,pda_q,asm_p,disks,1);	rf_ASMParityAdjust(asm_p->parityInfo,startAddrWithinStripe,endAddress,layoutPtr,asm_p);	rf_ASMParityAdjust(asm_p->qInfo,startAddrWithinStripe,endAddress,layoutPtr,asm_p);	break;      }  }  RF_ASSERT(asmList == NULL && pdaList == NULL);  /* make the header structure */  asm_hdr = rf_AllocAccessStripeMapHeader();  RF_ASSERT(numStripes == totStripes);  asm_hdr->numStripes = numStripes;  asm_hdr->stripeMap  = asm_list;  if (rf_mapDebug)    rf_PrintAccessStripeMap(asm_hdr);  return(asm_hdr);}/***************************************************************************************** * This routine walks through an ASM list and marks the PDAs that have failed. * It's called only when a disk failure causes an in-flight DAG to fail. * The parity may consist of two components, but we want to use only one failedPDA * pointer.  Thus we set failedPDA to point to the first parity component, and rely * on the rest of the code to do the right thing with this. ****************************************************************************************/void rf_MarkFailuresInASMList(raidPtr, asm_h)  RF_Raid_t                   *raidPtr;  RF_AccessStripeMapHeader_t  *asm_h;{  RF_RaidDisk_t  **disks = raidPtr->Disks;  RF_AccessStripeMap_t *asmap;  RF_PhysDiskAddr_t *pda;    for (asmap = asm_h->stripeMap; asmap; asmap = asmap->next) {    asmap->numDataFailed = asmap->numParityFailed = asmap->numQFailed = 0;    asmap->failedPDAtwo = asmap->failedPDA = NULL;    for (pda = asmap->physInfo; pda; pda=pda->next) {      if (RF_DEAD_DISK(disks[pda->row][pda->col].status)) {        asmap->numDataFailed++;        if (asmap->failedPDA)          asmap->failedPDAtwo = pda;        else          asmap->failedPDA = pda;      }    }    pda = asmap->parityInfo;    if (pda && RF_DEAD_DISK(disks[pda->row][pda->col].status)) {      asmap->numParityFailed++;      if (asmap->failedPDA)        asmap->failedPDAtwo = pda;      else        asmap->failedPDA = pda;    }    pda = asmap->qInfo;    if (pda && RF_DEAD_DISK(disks[pda->row][pda->col].status)) {      asmap->numQFailed++;      if (asmap->failedPDA)        asmap->failedPDAtwo = pda;      else        asmap->failedPDA = pda;    }  }}/***************************************************************************************** * * DuplicateASM -- duplicates an ASM and returns the new one * ****************************************************************************************/RF_AccessStripeMap_t *rf_DuplicateASM(asmap)  RF_AccessStripeMap_t  *asmap;{  RF_AccessStripeMap_t *new_asm;  RF_PhysDiskAddr_t *pda, *new_pda, *t_pda;  new_asm = rf_AllocAccessStripeMapComponent();  bcopy((char *)asmap, (char *)new_asm, sizeof(RF_AccessStripeMap_t));  new_asm->failedPDA = NULL;  new_asm->physInfo = NULL;  new_asm->parityInfo = NULL;  new_asm->next = NULL;  for (pda = asmap->physInfo; pda; pda=pda->next) {      /* copy the physInfo list */    t_pda = rf_AllocPhysDiskAddr();    bcopy((char *)pda, (char *)t_pda, sizeof(RF_PhysDiskAddr_t));    t_pda->next = NULL;    if (!new_asm->physInfo) {new_asm->physInfo = t_pda; new_pda = t_pda;}    else {new_pda->next = t_pda; new_pda = new_pda->next;}    if (pda == asmap->failedPDA) new_asm->failedPDA = t_pda;  }  for (pda = asmap->parityInfo; pda; pda=pda->next) {      /* copy the parityInfo list */    t_pda = rf_AllocPhysDiskAddr();    bcopy((char *)pda, (char *)t_pda, sizeof(RF_PhysDiskAddr_t));    t_pda->next = NULL;    if (!new_asm->parityInfo) {new_asm->parityInfo = t_pda; new_pda = t_pda;}    else {new_pda->next = t_pda; new_pda = new_pda->next;}    if (pda == asmap->failedPDA) new_asm->failedPDA = t_pda;  }  return(new_asm);}/***************************************************************************************** * * DuplicatePDA -- duplicates a PDA and returns the new one * ****************************************************************************************/RF_PhysDiskAddr_t *rf_DuplicatePDA(pda)  RF_PhysDiskAddr_t  *pda;{  RF_PhysDiskAddr_t *new;  new = rf_AllocPhysDiskAddr();  bcopy((char *)pda, (char *)new, sizeof(RF_PhysDiskAddr_t));  return(new);}/***************************************************************************************** * * routines to allocate and free list elements.  All allocation routines zero the * structure before returning it. * * FreePhysDiskAddr is static.  It should never be called directly, because * FreeAccessStripeMap takes care of freeing the PhysDiskAddr list. * ****************************************************************************************/static RF_FreeList_t *rf_asmhdr_freelist;#define RF_MAX_FREE_ASMHDR 128#define RF_ASMHDR_INC       16#define RF_ASMHDR_INITIAL   32static RF_FreeList_t *rf_asm_freelist;#define RF_MAX_FREE_ASM 192#define RF_ASM_INC       24#define RF_ASM_INITIAL   64static RF_FreeList_t *rf_pda_freelist;#define RF_MAX_FREE_PDA 192#define RF_PDA_INC       24#define RF_PDA_INITIAL   64/* called at shutdown time.  So far, all that is necessary is to release all the free lists */static void rf_ShutdownMapModule(ignored)  void  *ignored;{  RF_FREELIST_DESTROY(rf_asmhdr_freelist,next,(RF_AccessStripeMapHeader_t *));  RF_FREELIST_DESTROY(rf_pda_freelist,next,(RF_PhysDiskAddr_t *));  RF_FREELIST_DESTROY(rf_asm_freelist,next,(RF_AccessStripeMap_t *));}int rf_ConfigureMapModule(listp)  RF_ShutdownList_t  **listp;{	int rc;	RF_FREELIST_CREATE(rf_asmhdr_freelist, RF_MAX_FREE_ASMHDR,		RF_ASMHDR_INC, sizeof(RF_AccessStripeMapHeader_t));	if (rf_asmhdr_freelist == NULL) {		return(ENOMEM);	}	RF_FREELIST_CREATE(rf_asm_freelist, RF_MAX_FREE_ASM,		RF_ASM_INC, sizeof(RF_AccessStripeMap_t));	if (rf_asm_freelist == NULL) {		RF_FREELIST_DESTROY(rf_asmhdr_freelist,next,(RF_AccessStripeMapHeader_t *));		return(ENOMEM);	}	RF_FREELIST_CREATE(rf_pda_freelist, RF_MAX_FREE_PDA,		RF_PDA_INC, sizeof(RF_PhysDiskAddr_t));	if (rf_pda_freelist == NULL) {		RF_FREELIST_DESTROY(rf_asmhdr_freelist,next,(RF_AccessStripeMapHeader_t *));		RF_FREELIST_DESTROY(rf_pda_freelist,next,(RF_PhysDiskAddr_t *));		return(ENOMEM);	}	rc = rf_ShutdownCreate(listp, rf_ShutdownMapModule, NULL);	if (rc) {		RF_ERRORMSG3("Unable to add to shutdown list file %s line %d rc=%d\n", __FILE__,			__LINE__, rc);		rf_ShutdownMapModule(NULL);		return(rc);	}	RF_FREELIST_PRIME(rf_asmhdr_freelist, RF_ASMHDR_INITIAL,next,		(RF_AccessStripeMapHeader_t *));	RF_FREELIST_PRIME(rf_asm_freelist, RF_ASM_INITIAL,next,		(RF_AccessStripeMap_t *));	RF_FREELIST_PRIME(rf_pda_freelist, RF_PDA_INITIAL,next,		(RF_PhysDiskAddr_t *));	return(0);}RF_AccessStripeMapHeader_t *rf_AllocAccessStripeMapHeader(){	RF_AccessStripeMapHeader_t *p;	RF_FREELIST_GET(rf_asmhdr_freelist,p,next,(RF_AccessStripeMapHeader_t *));	bzero((char *)p, sizeof(RF_AccessStripeMapHeader_t));	return(p);}void rf_FreeAccessStripeMapHeader(p)  RF_AccessStripeMapHeader_t  *p;{	RF_FREELIST_FREE(rf_asmhdr_freelist,p,next);}RF_PhysDiskAddr_t *rf_AllocPhysDiskAddr(){	RF_PhysDiskAddr_t *p;	RF_FREELIST_GET(rf_pda_freelist,p,next,(RF_PhysDiskAddr_t *));	bzero((char *)p, sizeof(RF_PhysDiskAddr_t));	return(p);}/* allocates a list of PDAs, locking the free list only once * when we have to call calloc, we do it one component at a time to simplify * the process of freeing the list at program shutdown.  This should not be * much of a performance hit, because it should be very infrequently executed. */RF_PhysDiskAddr_t *rf_AllocPDAList(count)  int  count;{	RF_PhysDiskAddr_t *p;	RF_FREELIST_GET_N(rf_pda_freelist,p,next,(RF_PhysDiskAddr_t *),count);	return(p);}void rf_FreePhysDiskAddr(p)  RF_PhysDiskAddr_t  *p;{	RF_FREELIST_FREE(rf_pda_freelist,p,next);}static void rf_FreePDAList(l_start, l_end, count)  RF_PhysDiskAddr_t *l_start, *l_end;   /* pointers to start and end of list */  int count;                            /* number of elements in list */{	RF_FREELIST_FREE_N(rf_pda_freelist,l_start,next,(RF_PhysDiskAddr_t *),count);}RF_AccessStripeMap_t *rf_AllocAccessStripeMapComponent(){	RF_AccessStripeMap_t *p;	RF_FREELIST_GET(rf_asm_freelist,p,next,(RF_AccessStripeMap_t *));	bzero((char *)p, sizeof(RF_AccessStripeMap_t));	return(p);}/* this is essentially identical to AllocPDAList.  I should combine the two. * when we have to call calloc, we do it one component at a time to simplify * the process of freeing the list at program shutdown.  This should not be * much of a performance hit, because it should be very infrequently executed. */RF_AccessStripeMap_t *rf_AllocASMList(count)  int  count;{	RF_AccessStripeMap_t *p;	RF_FREELIST_GET_N(rf_asm_freelist,p,next,(RF_AccessStripeMap_t *),count);	return(p);}void rf_FreeAccessStripeMapComponent(p)  RF_AccessStripeMap_t  *p;{	RF_FREELIST_FREE(rf_asm_freelist,p,next);}static void rf_FreeASMList(l_start, l_end, count)  RF_AccessStripeMap_t  *l_start, *l_end;

⌨️ 快捷键说明

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