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

📄 fci.c

📁 winNT技术操作系统,国外开放的原代码和LIUX一样
💻 C
📖 第 1 页 / 共 5 页
字号:
        err, p_fci_internal->pv) != strlen(p_fci_internal->data_out)+1 ) {
      fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    p_fci_internal->sizeFileCFFILE2 += strlen(p_fci_internal->data_out)+1;

    /* cFiles is used to count all files of a cabinet */
    ++(p_fci_internal->cFiles);

    /* This is only true for files which will be written into the */
    /* next cabinet of the spanning folder */
    if( sizeOfFiles>payload ) {

      /* Files which data will be partially written into the current cabinet */
      if( cffile.iFolder==cffileCONTINUED_PREV_AND_NEXT ||
          cffile.iFolder==cffileCONTINUED_TO_NEXT
        ) {
        if( sizeOfFilesPrev<=payload ) {
          /* The size of the uncompressed, data of a spanning file in a */
          /* spanning data */
          cbFileRemainer=sizeOfFiles-payload;
        }
        cffile.iFolder=cffileCONTINUED_FROM_PREV;
      } else {
        cffile.iFolder=0;
      }

      /* write cffile into handleCFFILE1new */
      if( PFCI_WRITE(hfci, handleCFFILE1new, /* file handle */
          &cffile, /* memory buffer */
          sizeof(cffile), /* number of bytes to copy */
          err, p_fci_internal->pv) != sizeof(cffile) ) {
        fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
        return FALSE;
      }
      /* TODO error handling of err */

      *psizeFileCFFILE1new += sizeof(cffile);
      /* write name of file into handleCFFILE1new */
      if( PFCI_WRITE(hfci, handleCFFILE1new, /* file handle */
          p_fci_internal->data_out, /* memory buffer */
          strlen(p_fci_internal->data_out)+1, /* number of bytes to copy */
          err, p_fci_internal->pv) != strlen(p_fci_internal->data_out)+1 ) {
        fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
        return FALSE;
      }
      /* TODO error handling of err */

      *psizeFileCFFILE1new += strlen(p_fci_internal->data_out)+1;
    }

  } /* END OF while */
  p_fci_internal->cbFileRemainer=cbFileRemainer;
  return TRUE;
} /* end of fci_flushfolder_copy_cffile */




static BOOL fci_flush_folder(
	HFCI                  hfci,
	BOOL                  fGetNextCab,
	PFNFCIGETNEXTCABINET  pfnfcignc,
	PFNFCISTATUS          pfnfcis)
{
  int err;
  int handleCFDATA1new;                         /* handle for new  temp file */
  char szFileNameCFDATA1new[CB_MAX_FILENAME];  /* name buffer for temp file */
  int handleCFFILE1new;                         /* handle for new  temp file */
  char szFileNameCFFILE1new[CB_MAX_FILENAME];  /* name buffer for temp file */
  UINT cbReserveCFData, cbReserveCFFolder;
  char* reserved;
  cab_ULONG sizeFileCFDATA1new=0;
  cab_ULONG sizeFileCFFILE1new=0;
  cab_ULONG sizeFileCFDATA2old;
  cab_ULONG payload;
  cab_ULONG read_result;
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));

  /* test hfci */
  if (!REALLY_IS_FCI(hfci)) {
    SetLastError(ERROR_INVALID_HANDLE);
    return FALSE;
  }

  if ((!pfnfcignc) || (!pfnfcis)) {
    fci_set_error( FCIERR_NONE, ERROR_BAD_ARGUMENTS, TRUE );
    return FALSE;
  }

  if( p_fci_internal->fGetNextCabInVain &&
      p_fci_internal->fNextCab ){
    /* internal error */
    fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
    return FALSE;
  }

  /* If there was no FCIAddFile or FCIFlushFolder has already been called */
  /* this function will return TRUE */
  if( p_fci_internal->sizeFileCFFILE1 == 0 ) {
    if ( p_fci_internal->sizeFileCFDATA1 != 0 ) {
      /* error handling */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
    return TRUE;
  }

  if (p_fci_internal->data_in==NULL || p_fci_internal->data_out==NULL ) {
    /* error handling */
    fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
    return FALSE;
  }

  /* FCIFlushFolder has already been called... */
  if (p_fci_internal->fSplitFolder && p_fci_internal->sizeFileCFFILE2!=0) {
    return TRUE;
  }

  /* This can be set already, because it makes only a difference */
  /* when the current function exits with return FALSE */
  p_fci_internal->fSplitFolder=FALSE;


  if( p_fci_internal->fGetNextCabInVain ||
      p_fci_internal->fNextCab ){
    cbReserveCFData   = p_fci_internal->oldCCAB.cbReserveCFData;
    cbReserveCFFolder = p_fci_internal->oldCCAB.cbReserveCFFolder;
  } else {
    cbReserveCFData   = p_fci_internal->pccab->cbReserveCFData;
    cbReserveCFFolder = p_fci_internal->pccab->cbReserveCFFolder;
  }

  /* START of COPY */
  /* if there is data in p_fci_internal->data_in */
  if (p_fci_internal->cdata_in!=0) {

    if( !fci_flush_data_block(hfci, &err, pfnfcis) ) return FALSE;

  }
  /* reset to get the number of data blocks of this folder which are */
  /* actually in this cabinet ( at least partially ) */
  p_fci_internal->cDataBlocks=0;

  if ( p_fci_internal->fNextCab ||
       p_fci_internal->fGetNextCabInVain ) {
    read_result= p_fci_internal->oldCCAB.cbReserveCFHeader+
                 p_fci_internal->oldCCAB.cbReserveCFFolder;
    if ( p_fci_internal->oldCCAB.cbReserveCFHeader != 0 ||
        p_fci_internal->oldCCAB.cbReserveCFFolder != 0 ||
        p_fci_internal->oldCCAB.cbReserveCFData   != 0 ) {
      read_result+=4;
    }
  } else {
    read_result= p_fci_internal->pccab->cbReserveCFHeader+
                 p_fci_internal->pccab->cbReserveCFFolder;
    if ( p_fci_internal->pccab->cbReserveCFHeader != 0 ||
        p_fci_internal->pccab->cbReserveCFFolder != 0 ||
        p_fci_internal->pccab->cbReserveCFData   != 0 ) {
      read_result+=4;
    }
  }
  if (p_fci_internal->fPrevCab) {
    read_result+=strlen(p_fci_internal->szPrevCab)+1 +
      strlen(p_fci_internal->szPrevDisk)+1;
  }
  if (p_fci_internal->fNextCab) {
    read_result+=strlen(p_fci_internal->pccab->szCab)+1 +
      strlen(p_fci_internal->pccab->szDisk)+1;
  }

  p_fci_internal->statusFolderTotal = sizeof(CFHEADER)+read_result+
      sizeof(CFFOLDER) + p_fci_internal->sizeFileCFFILE2+
      p_fci_internal->sizeFileCFDATA2 + p_fci_internal->sizeFileCFFILE1+
      p_fci_internal->sizeFileCFDATA1 + p_fci_internal->sizeFileCFFOLDER;
  p_fci_internal->statusFolderCopied = 0;

  /* report status with pfnfcis about copied size of folder */
  if( (*pfnfcis)(statusFolder, p_fci_internal->statusFolderCopied,
      p_fci_internal->statusFolderTotal, /* TODO total folder size */
      p_fci_internal->pv) == -1) {
    fci_set_error( FCIERR_USER_ABORT, 0, TRUE );
    return FALSE;
  }

  /* get a new temp file */
  if(!PFCI_GETTEMPFILE(hfci,szFileNameCFDATA1new,CB_MAX_FILENAME)) {
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    return FALSE;
  }
  /* safety */
  if ( strlen(szFileNameCFDATA1new) >= CB_MAX_FILENAME ) {
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  handleCFDATA1new = PFCI_OPEN(hfci,szFileNameCFDATA1new,34050,384,&err,
    p_fci_internal->pv);
  if(handleCFDATA1new==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */



  /* get a new temp file */
  if(!PFCI_GETTEMPFILE(hfci,szFileNameCFFILE1new,CB_MAX_FILENAME)) {
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    PFCI_CLOSE(hfci,handleCFDATA1new,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    return FALSE;
  }
  /* safety */
  if ( strlen(szFileNameCFFILE1new) >= CB_MAX_FILENAME ) {
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    PFCI_CLOSE(hfci,handleCFDATA1new,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    return FALSE;
  }
  handleCFFILE1new = PFCI_OPEN(hfci,szFileNameCFFILE1new,34050,384,&err,
    p_fci_internal->pv);
  if(handleCFFILE1new==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  /* USE the variable read_result */
  if ( p_fci_internal->fNextCab ||
       p_fci_internal->fGetNextCabInVain ) {
    read_result= p_fci_internal->oldCCAB.cbReserveCFHeader;
    if ( p_fci_internal->oldCCAB.cbReserveCFHeader != 0 ||
        p_fci_internal->oldCCAB.cbReserveCFFolder != 0 ||
        p_fci_internal->oldCCAB.cbReserveCFData   != 0 ) {
      read_result+=4;
    }
  } else {
    read_result= p_fci_internal->pccab->cbReserveCFHeader;
    if ( p_fci_internal->pccab->cbReserveCFHeader != 0 ||
        p_fci_internal->pccab->cbReserveCFFolder != 0 ||
        p_fci_internal->pccab->cbReserveCFData   != 0 ) {
      read_result+=4;
    }
  }
  if (p_fci_internal->fPrevCab) {
    read_result+=strlen(p_fci_internal->szPrevCab)+1 +
      strlen(p_fci_internal->szPrevDisk)+1;
  }
  read_result+= sizeof(CFHEADER) + p_fci_internal->sizeFileCFDATA2 +
    p_fci_internal->sizeFileCFFILE2 + p_fci_internal->sizeFileCFFOLDER;

  if(p_fci_internal->sizeFileCFFILE1!=0) {
    read_result+= sizeof(CFFOLDER)+p_fci_internal->pccab->cbReserveCFFolder;
  }

  /* Check if multiple cabinets have to be created. */

  /* Might be too much data for the maximum allowed cabinet size.*/
  /* When any further data will be added later, it might not */
  /* be possible to flush the cabinet, because there might */
  /* not be enough space to store the name of the following */
  /* cabinet and name of the corresponding disk. */
  /* So take care of this and get the name of the next cabinet */
  if( p_fci_internal->fGetNextCabInVain==FALSE &&
      p_fci_internal->fNextCab==FALSE &&
      (
        (
          p_fci_internal->pccab->cb < read_result +
          p_fci_internal->sizeFileCFDATA1 +
          p_fci_internal->sizeFileCFFILE1 +
          CB_MAX_CABINET_NAME +   /* next cabinet name */
          CB_MAX_DISK_NAME        /* next disk name */
        ) || fGetNextCab
      )
  ) {
    /* save CCAB */
    memcpy(&(p_fci_internal->oldCCAB), p_fci_internal->pccab, sizeof(CCAB));
    /* increment cabinet index */
    ++(p_fci_internal->pccab->iCab);
    /* get name of next cabinet */
    p_fci_internal->estimatedCabinetSize=p_fci_internal->statusFolderTotal;
    if (!(*pfnfcignc)(p_fci_internal->pccab,
        p_fci_internal->estimatedCabinetSize, /* estimated size of cab */
        p_fci_internal->pv)) {
      /* error handling */
      fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
      PFCI_CLOSE(hfci,handleCFDATA1new,&err,p_fci_internal->pv);
      /* TODO error handling of err */
      PFCI_CLOSE(hfci,handleCFFILE1new,&err,p_fci_internal->pv);
      /* TODO error handling of err */
      return FALSE;
    }

    /* Skip a few lines of code. This is catched by the next if. */
    p_fci_internal->fGetNextCabInVain=TRUE;
  }

  /* too much data for cabinet */
  if( (p_fci_internal->fGetNextCabInVain ||
        p_fci_internal->fNextCab ) &&
      (
        (
          p_fci_internal->oldCCAB.cb < read_result +
          p_fci_internal->sizeFileCFDATA1 +
          p_fci_internal->sizeFileCFFILE1 +
          strlen(p_fci_internal->pccab->szCab)+1 +   /* next cabinet name */
          strlen(p_fci_internal->pccab->szDisk)+1    /* next disk name */
        ) || fGetNextCab
      )
  ) {
    p_fci_internal->fGetNextCabInVain=FALSE;
    p_fci_internal->fNextCab=TRUE;

    /* return FALSE if there is not enough space left*/
    /* this should never happen */
    if (p_fci_internal->oldCCAB.cb <=
        p_fci_internal->sizeFileCFFILE1 +
        read_result +
        strlen(p_fci_internal->pccab->szCab)+1 + /* next cabinet name */
        strlen(p_fci_internal->pccab->szDisk)+1  /* next disk name */
    ) {

      PFCI_CLOSE(hfci,handleCFDATA1new,&err,p_fci_internal->pv);
      /* TODO error handling of err */
      PFCI_DELETE(hfci,szFileNameCFDATA1new,&err,p_fci_internal->pv);
      /* TODO error handling of err */

      /* close and delete p_fci_internal->handleCFFILE1 */
      PFCI_CLOSE(hfci,handleCFFILE1new,&err,p_fci_internal->pv);
      /* TODO error handling of err */
      PFCI_DELETE(hfci,szFileNameCFFILE1new,&err,p_fci_internal->pv);
      /* TODO error handling of err */

      return FALSE;
    }

    /* the folder will be split across cabinets */
    p_fci_internal->fSplitFolder=TRUE;

  } else {
    /* this should never happen */
    if (p_fci_internal->fNextCab) {
      /* internal error */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
  }

⌨️ 快捷键说明

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