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

📄 protectp.c

📁 DOC文件系统驱动源代码
💻 C
📖 第 1 页 / 共 2 页
字号:

  status = chkASICmode(flash);
  if(status != flOK)
    return status;

  *flag = KEY_INSERTED | LOCK_ASSERTED; /* initiate the flags */

  for (floor = 0;floor < flash->noOfFloors;floor++)
  {
     setFloor(flash,floor);

     /* read data protect structure status */

     switch (area)
     {
        case 0: /* data protect structure 0 */

           protectData = flRead8bitRegPlus(flash,NdataProtect0Status) ;
           break;

        case 1: /* data protect structure 1 */

           protectData = flRead8bitRegPlus(flash,NdataProtect1Status) ;
           *flag      |= CHANGEABLE_PROTECTION;
           break;

        default: /* No such protection area */

           return flGeneralFailure;
     }

     curFlag = FALSE;
     /* Check if area is write protected */
     if((protectData & PROTECT_STAT_WP_MASK) == PROTECT_STAT_WP_MASK)
     {
        status = protectionBoundries(flash, area, &addressLow,
                                         &addressHigh, floor);
        if(status != flOK)
           return status;

        /* Ignore default protection - write protect with key */
        /* "00000000" on DPS                                  */
        addressLow  = addressLow  >> flash->erasableBlockSizeBits;
        addressHigh = addressHigh >> flash->erasableBlockSizeBits;

        if(( /* 32MB DiskOnChip and protection is on the DPS    */
             (flash->mediaType == MDOCP_TYPE               ) &&
             ( (addressLow != (CardAddress)(area + 1) ) ||
               (addressLow != addressHigh             )    )    ) ||
             /* or 16MB DiskOnChip and protection is on the DPS */
           ( (flash->mediaType == MDOCP_16_TYPE                 ) &&
             ( (addressLow != (CardAddress)((area<<1) + 1) ) ||
               (addressLow + 1 != addressHigh              )    )    ))
        {
           *flag |= WRITE_PROTECTED;
           curFlag = TRUE;
        }
     }
     /* Check if area is read protected */
     if((protectData & PROTECT_STAT_RP_MASK) ==PROTECT_STAT_RP_MASK)
     {
        *flag |= READ_PROTECTED;
        curFlag = TRUE;
     }
     /* Check if key is corrently inserted */
     if(((protectData & PROTECT_STAT_KEY_OK_MASK) !=
         PROTECT_STAT_KEY_OK_MASK) && (curFlag == TRUE))
        *flag &= ~KEY_INSERTED;
     /* Check if HW signal is enabled */
     if((protectData & PROTECT_STAT_LOCK_MASK) == PROTECT_STAT_LOCK_MASK)
        *flag |=LOCK_ENABLED ;
     /* Check if HW signal is asserted */
     if((flRead8bitRegPlus(flash,NprotectionStatus) &
        PROTECT_STAT_LOCK_INPUT_MASK) ==  PROTECT_STAT_LOCK_INPUT_MASK)
        *flag &= ~LOCK_ASSERTED;
  }
  return(flOK);
}

#ifndef FL_READ_ONLY

static byte findChecksum(byte * buffer, word size)
{
   register int i;
   byte answer;

   answer = 0xff;
   for(i=0 ; i<size ; i++)
     answer -= buffer[i];
   return answer;
}

/*
 ** SetProtection
 *
 *
 *  PARAMETERS:
 *  flash       : Pointer identifying drive
 *  area        : indicated which protection area to work on.  0 or 1.
 *  AddressLow  : sets address of lower boundary of protected area. 0 - floor size.
 *  AddressHigh : sets address of upper boundary of protected area. AddressLow - floor size.
 *  Key         : an 8 byte long array containing the protection password.
 *  flag        : any combination of the following flags:
 *      LOCK_ENABLED    - The LOCK signal is enabled.
 *      READ_PROTECTED - The area is protected against read operations
 *      WRITE_PROTECTED - The area is protected against write operations
 *  modes       : Either COMMIT_PROTECTION will cause the new values to
 *                take affect immidiatly or DO_NOT_COMMIT_PROTECTION for
 *                delaying the new values to take affect only after the
 *                next reset.
 *
 *  DESCRIPTION:  Sets the definitions of a protected area: location, key and protection type
 *
 *  RETURNS:
 *    flOK           - success
 *    FlWriteProtect - protection violetion,
 *    FlReadProtect  - protection violetion.
 *    FlDataError    - any other read failure.
 *    FlWriteFault   - any other write error.
 *    flBadLength    - if the length of the protected area exceeds
 *                     allowed length
 */

FLStatus protectionSet ( FLFlash * flash, byte area, word flag,
                         CardAddress addressLow, CardAddress addressHigh,
                         byte FAR1*  key , byte modes, byte floorNo)
{
  FLBoolean restoreInterleave = FALSE;
  byte      downloadStatus;
  DPSStruct dps;
  dword     floorInc = floorNo * NFDC21thisVars->floorSize;
  word      goodUnit,redundantUnit;
  dword     goodDPS,redundantDPS;
  FLStatus  status;
  dword     goodIPL      = 0; /* Initialized to remove warrnings */
  dword     redundantIPL = 0; /* Initialized to remove warrnings */
  dword     copyOffset;       /* Offset to redundant DPS unit    */
  dword     ipl0Copy0;     /* Offset to IPL second 512 bytes copy 0     */
  dword     dps1Copy0;     /* Offset to DPS1 copy 0                     */
  word      dps1UnitNo;    /* Offset to redundant DPS unit              */


  status = chkASICmode(flash);
  if(status != flOK)
    return status;

  /* check if exceeds the size */
  if( (addressLow > addressHigh) ||
      (addressHigh - addressLow >= (dword)NFDC21thisVars->floorSize))
     return( flBadLength );

  /* change to interleave 1 */
  if ( flash->interleaving == 2)
  {
     restoreInterleave = TRUE;
     status = changeInterleave(flash,1);
     if(status != flOK)
       return status;
  }

  if(flash->mediaType == MDOCP_TYPE) /* DiskOnChip Millennium Plus 32MB */
  {
    copyOffset   = flash->chipSize>>1; /* The chips are consequtive */
    dps1Copy0    = DPS1_COPY0_32;
    dps1UnitNo   = DPS1_UNIT_NO_32;
    ipl0Copy0    = IPL0_COPY0_32;
  }
  else
  {
    copyOffset   = flash->erasableBlockSize; /* The chips are consequtive */
    dps1Copy0    = DPS1_COPY0_16;
    dps1UnitNo   = DPS1_UNIT_NO_16;
    ipl0Copy0    = IPL0_COPY0_16;
  }

  /* find if previous download */
  downloadStatus = flRead8bitRegPlus(flash,NdownloadStatus);

  /* prepare buffer */

  switch (area)
  {
     case 0: /* data protect structure 0 */

        switch (downloadStatus & DWN_STAT_DPS0_ERR)
        {
           case DWN_STAT_DPS01_ERR: /* Both  are bad */
              return flBadDownload;

           case DWN_STAT_DPS00_ERR: /* First is  bad */
              redundantUnit = (word)(DPS0_UNIT_NO + floorNo * (NFDC21thisVars->floorSize>>flash->erasableBlockSizeBits));
              goodUnit      = (word)(redundantUnit + (copyOffset>>flash->erasableBlockSizeBits));
              goodDPS       = DPS0_COPY0+floorInc + copyOffset;
              redundantDPS  = DPS0_COPY0+floorInc;
              break;

           default:                 /* Both copies are good */
              goodUnit      = (word)(DPS0_UNIT_NO + floorNo*(NFDC21thisVars->floorSize>>flash->erasableBlockSizeBits));
              redundantUnit = (word)(goodUnit + (copyOffset>>flash->erasableBlockSizeBits));
              goodDPS       = DPS0_COPY0+floorInc;
              redundantDPS  = DPS0_COPY0+floorInc + copyOffset;
        }
        break;

     case 1: /* data protect structure 0 */

        switch (downloadStatus & DWN_STAT_DPS1_ERR)
        {
           case DWN_STAT_DPS11_ERR: /* Both  are bad */
              return flBadDownload;

           case DWN_STAT_DPS10_ERR: /* First is  bad */
              redundantUnit = (word)(dps1UnitNo + floorNo*(NFDC21thisVars->floorSize>>flash->erasableBlockSizeBits));
              goodUnit      = (word)(redundantUnit + (copyOffset>>flash->erasableBlockSizeBits));
              goodDPS       = dps1Copy0+floorInc + copyOffset;
              redundantDPS  = dps1Copy0+floorInc;
              redundantIPL  = ipl0Copy0 + floorInc;
              goodIPL       = redundantIPL + copyOffset;
              break;

           default :                /* First is good */
              goodUnit      = (word)(dps1UnitNo + floorNo*(NFDC21thisVars->floorSize>>flash->erasableBlockSizeBits));
              redundantUnit = (word)(goodUnit + (copyOffset>>flash->erasableBlockSizeBits));
              goodDPS       = dps1Copy0+floorInc;
              redundantDPS  = dps1Copy0+floorInc + copyOffset;
              goodIPL       = ipl0Copy0 + floorInc;
              redundantIPL  = goodIPL + copyOffset;
        }
        break;

     default: /* No such protection area */

        return flGeneralFailure;
  }

  /* Build new DPS */
  if (key==NULL) /* key must be retreaved from previous structure */
  {
     status = flash->read(flash,goodDPS,(void FAR1 *)&dps,SIZE_OF_DPS,0);
     if(status!=flOK) goto END_WRITE_DPS;
     if(findChecksum((byte *)&dps,SIZE_OF_DPS)!=0) /* bad copy */
        status = flash->read(flash,goodDPS+REDUNDANT_DPS_OFFSET,
                          (void FAR1*)&dps,SIZE_OF_DPS,0);
     makeDPS(addressLow,addressHigh,(byte FAR1*)(dps.key),flag,
             (byte *)&dps,flash->mediaType);
  }
  else           /* key is given as a parameter */
  {
     makeDPS(addressLow,addressHigh,(byte FAR1*)key,flag,
             (byte *)&dps,flash->mediaType);
  }

  /* Erase redundant unit       */
  status = flash->erase(flash,redundantUnit,1);
  if(status!=flOK) goto END_WRITE_DPS;

  /* Write new DPS              */
  status = flash->write(flash,redundantDPS,&dps,SIZE_OF_DPS,0);
  if(status!=flOK) goto END_WRITE_DPS;
  status = flash->write(flash,redundantDPS + REDUNDANT_DPS_OFFSET,
                     &dps,SIZE_OF_DPS,0);
  if(status!=flOK) goto END_WRITE_DPS;

  if (area == 1) /* copy the IPL */
  {
#ifndef MTD_STANDALONE
     /* Force remapping of internal catched sector */
     flash->socket->remapped = TRUE;
#endif /* MTD_STANDALONE */

     /* Read first 512 bytes IPL   */
     status = flash->read(flash,goodIPL,NFDC21thisBuffer,SECTOR_SIZE,0);
     if(status!=flOK) goto END_WRITE_DPS;

     /* Write first 512 bytes IPL  */
     status = flash->write(flash,redundantIPL,NFDC21thisBuffer,SECTOR_SIZE,EDC);
     if(status!=flOK) goto END_WRITE_DPS;
     status = flash->write(flash,redundantIPL + SECTOR_SIZE,
                        NFDC21thisBuffer,SECTOR_SIZE,EDC);
     if(status!=flOK) goto END_WRITE_DPS;

     /* Read second 512 bytes IPL  */
     status = flash->read(flash,goodIPL + IPL_HIGH_SECTOR,
                       NFDC21thisBuffer,SECTOR_SIZE,0);
     if(status!=flOK) goto END_WRITE_DPS;

     /* Write second 512 bytes IPL */
     status = flash->write(flash,redundantIPL + IPL_HIGH_SECTOR,
                        NFDC21thisBuffer,SECTOR_SIZE,EDC);
     if(status!=flOK) goto END_WRITE_DPS;
     status = flash->write(flash,redundantIPL + IPL_HIGH_SECTOR +
            SECTOR_SIZE, NFDC21thisBuffer,SECTOR_SIZE,EDC);
     if(status!=flOK) goto END_WRITE_DPS;
     /* Read Srong Arm mark */
     status = flash->read(flash,goodIPL + IPL_HIGH_SECTOR + 8,
                       NFDC21thisBuffer,1,EXTRA);
     if(status!=flOK) goto END_WRITE_DPS;
     /* Write Srong Arm mark */
     status = flash->write(flash,redundantIPL + IPL_HIGH_SECTOR + 8 +
            SECTOR_SIZE, NFDC21thisBuffer,1,EXTRA);
     if(status!=flOK) goto END_WRITE_DPS;
     status = flash->write(flash,redundantIPL + IPL_HIGH_SECTOR + 8,
                        NFDC21thisBuffer,1,EXTRA);
     if(status!=flOK) goto END_WRITE_DPS;
  }

  /* Erase good unit         */
  status = flash->erase(flash,goodUnit,1);
  if(status!=flOK) goto END_WRITE_DPS;

  /* Write over previous DPS */
  status = flash->write(flash,goodDPS,&dps,SIZE_OF_DPS,0);
  if(status!=flOK) goto END_WRITE_DPS;
  status = flash->write(flash,goodDPS + REDUNDANT_DPS_OFFSET,
                     &dps,SIZE_OF_DPS,0);
  if(status!=flOK) goto END_WRITE_DPS;

  if (area == 1) /* copy the IPL */
  {
     /* Read first 512 bytes IPL   */
     status = flash->read(flash,redundantIPL,NFDC21thisBuffer,SECTOR_SIZE,0);
     if(status!=flOK) goto END_WRITE_DPS;

     /* Write first 512 bytes IPL  */
     status = flash->write(flash,goodIPL,NFDC21thisBuffer,SECTOR_SIZE,EDC);
     if(status!=flOK) goto END_WRITE_DPS;
     status = flash->write(flash,goodIPL + SECTOR_SIZE,
                        NFDC21thisBuffer,SECTOR_SIZE,EDC);
     if(status!=flOK) goto END_WRITE_DPS;

     /* Read second 512 bytes IPL  */
     status = flash->read(flash,redundantIPL + IPL_HIGH_SECTOR,
                       NFDC21thisBuffer,SECTOR_SIZE,0);
     if(status!=flOK) goto END_WRITE_DPS;

     /* Write second 512 bytes IPL */
     status = flash->write(flash,goodIPL + IPL_HIGH_SECTOR,
                        NFDC21thisBuffer,SECTOR_SIZE,EDC);
     if(status!=flOK) goto END_WRITE_DPS;
     status = flash->write(flash,goodIPL + IPL_HIGH_SECTOR +
                        SECTOR_SIZE, NFDC21thisBuffer,
                        SECTOR_SIZE,EDC);
     if(status!=flOK) goto END_WRITE_DPS;
  }

END_WRITE_DPS:
  if ( restoreInterleave == TRUE)
  {
     FLStatus status2;

     chkASICmode(flash);                   /* Release posible access error */
     status2 = changeInterleave(flash, 2); /* change back to interleave 2 */
     if(status2 != flOK)
        return status2;
  }
  if (status == flOK)
  {
     if ((modes & COMMIT_PROTECTION) && /* The new values will take affect now */
         (flash->download != NULL))
        status = flash->download(flash);
  }
  return status;

}

/*
 ** makeDataProtectStruct
 *
 *
 *  PARAMETERS:
 *  AddressLow  : sets address of lower boundary of protected area
 *  AddressHigh: sets address of upper boundary of protected area
 *  Key     : an 8 byte long array containing the protection password.
 *  flag        : any combination of the following flags:
 *      LOCK_ENABLED    - The LOCK signal is enabled.
 *      READ_PROTECTED - The area is protected against read operations
 *      WRITE_PROTECTED - The area is protected against write operations
 *  buffer - buffer pointer of the returned structure.
 *  flashType - The flash->mediaType value (either MDOCP_TYPE/MDOCP_16_TYPE
 *
 *  DESCRIPTION:  Sets the definitions of a protected structure: location, key and protection type
 *
 *  RETURNS:
 *
 */

static void makeDPS(CardAddress addressLow, CardAddress addressHigh,
             byte FAR1* key , word flag, byte* buffer, byte flashType)
{
    int i = 10;
    DPSStruct* dps = (DPSStruct *)buffer;

    if(flashType == MDOCP_16_TYPE)
      i--;

    /* convert to little endien and store */
    toLE4(dps->addressLow,addressLow   >> i);
    toLE4(dps->addressHigh,addressHigh >> i);

    /*insert protection key */
    for(i=0; i<PROTECTION_KEY_LENGTH; i++)
        dps->key[i] = key[i];

    /* insert flags */
    dps->protectionType = 0;
    if((flag & LOCK_ENABLED)==LOCK_ENABLED)
        dps->protectionType |= DPS_LOCK_ENABLED;
    if((flag & READ_PROTECTED)==READ_PROTECTED)
        dps->protectionType |= DPS_READ_PROTECTED;
    if((flag & WRITE_PROTECTED)==WRITE_PROTECTED)
        dps->protectionType |= DPS_WRITE_PROTECTED;

    /* calculate and store checksum */
    dps->checksum = findChecksum(buffer,SIZE_OF_DPS-1);
}
#endif /* FL_READ_ONLY */
#endif   /*  HW_PROTECTION */



⌨️ 快捷键说明

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