/*
 * File Compression Interface
 *
 * Copyright 2002 Patrik Stridvall
 * Copyright 2005 Gerold Jens Wucherpfennig
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

/*

There is still some work to be done:

- no real compression yet
- unknown behaviour if files>=2GB or cabinet >=4GB
- check if the maximum size for a cabinet is too small to store any data
- call pfnfcignc on exactly the same position as MS FCIAddFile in every case
- probably check err

*/



#include "config.h"

#include <stdarg.h>
#include <stdio.h>
#include <string.h>

#include "windef.h"
#include "winbase.h"
#include "winerror.h"
#include "winternl.h"
#include "fci.h"
#include "cabinet.h"
#include "wine/debug.h"


#ifdef WORDS_BIGENDIAN
#define fci_endian_ulong(x) RtlUlongByteSwap(x)
#define fci_endian_uword(x) RtlUshortByteSwap(x)
#else
#define fci_endian_ulong(x) (x)
#define fci_endian_uword(x) (x)
#endif


#define fci_set_error(A,B,C) do {      \
    p_fci_internal->perf->erfOper = A; \
    p_fci_internal->perf->erfType = B; \
    p_fci_internal->perf->fError =  C; \
    if (B) SetLastError(B); } while(0)


typedef struct {
  cab_UBYTE signature[4]; /* !CAB for unfinished cabinets else MSCF */
  cab_ULONG reserved1;
  cab_ULONG cbCabinet;    /*  size of the cabinet file in bytes*/
  cab_ULONG reserved2;
  cab_ULONG coffFiles;    /* offset to first CFFILE section */
  cab_ULONG reserved3;
  cab_UBYTE versionMinor; /* 3 */
  cab_UBYTE versionMajor; /* 1 */
  cab_UWORD cFolders;     /* number of CFFOLDER entries in the cabinet*/
  cab_UWORD cFiles;       /* number of CFFILE entries in the cabinet*/
  cab_UWORD flags;        /* 1=prev cab, 2=next cabinet, 4=reserved sections*/
  cab_UWORD setID;        /* identification number of all cabinets in a set*/
  cab_UWORD iCabinet;     /* number of the cabinet in a set */
  /* additional area if "flags" were set*/
} CFHEADER; /* minimum 36 bytes */

typedef struct {
  cab_ULONG coffCabStart; /* offset to the folder's first CFDATA section */
  cab_UWORD cCFData;      /* number of this folder's CFDATA sections */
  cab_UWORD typeCompress; /* compression type of data in CFDATA section*/
  /* additional area if reserve flag was set */
} CFFOLDER; /* minimum 8 bytes */

typedef struct {
  cab_ULONG cbFile;          /* size of the uncompressed file in bytes */
  cab_ULONG uoffFolderStart; /* offset of the uncompressed file in the folder */
  cab_UWORD iFolder;         /* number of folder in the cabinet 0=first  */
                             /* for special values see below this structure*/
  cab_UWORD date;            /* last modification date*/
  cab_UWORD time;            /* last modification time*/
  cab_UWORD attribs;         /* DOS fat attributes and UTF indicator */
  /* ... and a C string with the name of the file */
} CFFILE; /* 16 bytes + name of file */


typedef struct {
  cab_ULONG csum;          /* checksum of this entry*/
  cab_UWORD cbData;        /* number of compressed bytes  */
  cab_UWORD cbUncomp;      /* number of bytes when data is uncompressed */
  /* optional reserved area */
  /* compressed data */
} CFDATA;


/***********************************************************************
 *		FCICreate (CABINET.10)
 *
 * FCICreate is provided with several callbacks and
 * returns a handle which can be used to create cabinet files.
 *
 * PARAMS
 *   perf       [IO]  A pointer to an ERF structure.  When FCICreate
 *                    returns an error condition, error information may
 *                    be found here as well as from GetLastError.
 *   pfnfiledest [I]  A pointer to a function which is called when a file
 *                    is placed. Only useful for subsequent cabinet files.
 *   pfnalloc    [I]  A pointer to a function which allocates ram.  Uses
 *                    the same interface as malloc.
 *   pfnfree     [I]  A pointer to a function which frees ram.  Uses the
 *                    same interface as free.
 *   pfnopen     [I]  A pointer to a function which opens a file.  Uses
 *                    the same interface as _open.
 *   pfnread     [I]  A pointer to a function which reads from a file into
 *                    a caller-provided buffer.  Uses the same interface
 *                    as _read.
 *   pfnwrite    [I]  A pointer to a function which writes to a file from
 *                    a caller-provided buffer.  Uses the same interface
 *                    as _write.
 *   pfnclose    [I]  A pointer to a function which closes a file handle.
 *                    Uses the same interface as _close.
 *   pfnseek     [I]  A pointer to a function which seeks in a file.
 *                    Uses the same interface as _lseek.
 *   pfndelete   [I]  A pointer to a function which deletes a file.
 *   pfnfcigtf   [I]  A pointer to a function which gets the name of a
 *                    temporary file.
 *   pccab       [I]  A pointer to an initialized CCAB structure.
 *   pv          [I]  A pointer to an application-defined notification
 *                    function which will be passed to other FCI functions
 *                    as a parameter.
 *
 * RETURNS
 *   On success, returns an FCI handle of type HFCI.
 *   On failure, the NULL file handle is returned. Error
 *   info can be retrieved from perf.
 *
 * INCLUDES
 *   fci.h
 *
 */
HFCI __cdecl FCICreate(
	PERF perf,
	PFNFCIFILEPLACED   pfnfiledest,
	PFNFCIALLOC        pfnalloc,
	PFNFCIFREE         pfnfree,
	PFNFCIOPEN         pfnopen,
	PFNFCIREAD         pfnread,
	PFNFCIWRITE        pfnwrite,
	PFNFCICLOSE        pfnclose,
	PFNFCISEEK         pfnseek,
	PFNFCIDELETE       pfndelete,
	PFNFCIGETTEMPFILE  pfnfcigtf,
	PCCAB              pccab,
	void *pv)
{
  HFCI hfci;
  int err;
  PFCI_Int p_fci_internal;

  if (!perf) {
    SetLastError(ERROR_BAD_ARGUMENTS);
    return NULL;
  }
  if ((!pfnalloc) || (!pfnfree) || (!pfnopen) || (!pfnread) ||
      (!pfnwrite) || (!pfnclose) || (!pfnseek) || (!pfndelete) ||
      (!pfnfcigtf) || (!pccab)) {
    perf->erfOper = FCIERR_NONE;
    perf->erfType = ERROR_BAD_ARGUMENTS;
    perf->fError = TRUE;

    SetLastError(ERROR_BAD_ARGUMENTS);
    return NULL;
  }

  if (!((hfci = (*pfnalloc)(sizeof(FCI_Int))))) {
    perf->erfOper = FCIERR_ALLOC_FAIL;
    perf->erfType = ERROR_NOT_ENOUGH_MEMORY;
    perf->fError = TRUE;

    SetLastError(ERROR_NOT_ENOUGH_MEMORY);
    return NULL;
  }

  p_fci_internal=((PFCI_Int)(hfci));
  p_fci_internal->FCI_Intmagic = FCI_INT_MAGIC;
  p_fci_internal->perf = perf;
  p_fci_internal->pfnfiledest = pfnfiledest;
  p_fci_internal->pfnalloc = pfnalloc;
  p_fci_internal->pfnfree = pfnfree;
  p_fci_internal->pfnopen = pfnopen;
  p_fci_internal->pfnread = pfnread;
  p_fci_internal->pfnwrite = pfnwrite;
  p_fci_internal->pfnclose = pfnclose;
  p_fci_internal->pfnseek = pfnseek;
  p_fci_internal->pfndelete = pfndelete;
  p_fci_internal->pfnfcigtf = pfnfcigtf;
  p_fci_internal->pccab = pccab;
  p_fci_internal->fPrevCab = FALSE;
  p_fci_internal->fNextCab = FALSE;
  p_fci_internal->fSplitFolder = FALSE;
  p_fci_internal->fGetNextCabInVain = FALSE;
  p_fci_internal->pv = pv;
  p_fci_internal->data_in  = NULL;
  p_fci_internal->cdata_in = 0;
  p_fci_internal->data_out = NULL;
  p_fci_internal->cCompressedBytesInFolder = 0;
  p_fci_internal->cFolders = 0;
  p_fci_internal->cFiles = 0;
  p_fci_internal->cDataBlocks = 0;
  p_fci_internal->sizeFileCFDATA1 = 0;
  p_fci_internal->sizeFileCFFILE1 = 0;
  p_fci_internal->sizeFileCFDATA2 = 0;
  p_fci_internal->sizeFileCFFILE2 = 0;
  p_fci_internal->sizeFileCFFOLDER = 0;
  p_fci_internal->sizeFileCFFOLDER = 0;
  p_fci_internal->fNewPrevious = FALSE;
  p_fci_internal->estimatedCabinetSize = 0;
  p_fci_internal->statusFolderTotal = 0;

  memset(&p_fci_internal->oldCCAB, 0, sizeof(CCAB));
  memcpy(p_fci_internal->szPrevCab, pccab->szCab, CB_MAX_CABINET_NAME);
  memcpy(p_fci_internal->szPrevDisk, pccab->szDisk, CB_MAX_DISK_NAME);

  /* CFDATA */
  if( !PFCI_GETTEMPFILE(hfci,p_fci_internal->szFileNameCFDATA1,
      CB_MAX_FILENAME)) {
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    return FALSE;
  }
  /* safety */
  if ( strlen(p_fci_internal->szFileNameCFDATA1) >= CB_MAX_FILENAME ) {
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }

  p_fci_internal->handleCFDATA1 = PFCI_OPEN(hfci,
    p_fci_internal->szFileNameCFDATA1, 34050, 384, &err, pv);
  if(p_fci_internal->handleCFDATA1==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error checking of err */

  /* array of all CFFILE in a folder */
  if( !PFCI_GETTEMPFILE(hfci,p_fci_internal->szFileNameCFFILE1,
      CB_MAX_FILENAME)) {
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    return FALSE;
  }
  /* safety */
  if ( strlen(p_fci_internal->szFileNameCFFILE1) >= CB_MAX_FILENAME ) {
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  p_fci_internal->handleCFFILE1 = PFCI_OPEN(hfci,
    p_fci_internal->szFileNameCFFILE1, 34050, 384, &err, pv);
  if(p_fci_internal->handleCFFILE1==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error checking of err */

  /* CFDATA with checksum and ready to be copied into cabinet */
  if( !PFCI_GETTEMPFILE(hfci,p_fci_internal->szFileNameCFDATA2,
      CB_MAX_FILENAME)) {
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE);
    return FALSE;
  }
  /* safety */
  if ( strlen(p_fci_internal->szFileNameCFDATA2) >= CB_MAX_FILENAME ) {
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  p_fci_internal->handleCFDATA2 = PFCI_OPEN(hfci,
    p_fci_internal->szFileNameCFDATA2, 34050, 384, &err, pv);
  if(p_fci_internal->handleCFDATA2==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error checking of err */

  /* array of all CFFILE in a folder, ready to be copied into cabinet */
  if( !PFCI_GETTEMPFILE(hfci,p_fci_internal->szFileNameCFFILE2,
      CB_MAX_FILENAME)) {
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    return FALSE;
  }
  /* safety */
  if ( strlen(p_fci_internal->szFileNameCFFILE2) >= CB_MAX_FILENAME ) {
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  p_fci_internal->handleCFFILE2 = PFCI_OPEN(hfci,
    p_fci_internal->szFileNameCFFILE2, 34050, 384, &err, pv);
  if(p_fci_internal->handleCFFILE2==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error checking of err */

  /* array of all CFFILE in a folder, ready to be copied into cabinet */
  if( !PFCI_GETTEMPFILE(hfci,p_fci_internal->szFileNameCFFOLDER,
      CB_MAX_FILENAME)) {
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    return FALSE;
  }
  /* safety */
  if ( strlen(p_fci_internal->szFileNameCFFOLDER) >= CB_MAX_FILENAME ) {
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  p_fci_internal->handleCFFOLDER = PFCI_OPEN(hfci,
    p_fci_internal->szFileNameCFFOLDER, 34050, 384, &err, pv);
  if(p_fci_internal->handleCFFOLDER==0) {
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE);
    return FALSE;
  }

  /* TODO close and delete new files when return FALSE */
  /* TODO error checking of err */

  return hfci;
} /* end of FCICreate */






static BOOL fci_flush_data_block (HFCI hfci, int* err,
    PFNFCISTATUS pfnfcis) {

  /* attention no hfci checks!!! */
  /* attention no checks if there is data available!!! */
  CFDATA data;
  CFDATA* cfdata=&data;
  char* reserved;
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));
  UINT cbReserveCFData=p_fci_internal->pccab->cbReserveCFData;
  UINT i;

  /* TODO compress the data of p_fci_internal->data_in */
  /* and write it to p_fci_internal->data_out */
  memcpy(p_fci_internal->data_out, p_fci_internal->data_in,
    p_fci_internal->cdata_in /* number of bytes to copy */);

  cfdata->csum=0; /* checksum has to be set later */
  /* TODO set realsize of compressed data */
  cfdata->cbData   = p_fci_internal->cdata_in;
  cfdata->cbUncomp = p_fci_internal->cdata_in;

  /* write cfdata to p_fci_internal->handleCFDATA1 */
  if( PFCI_WRITE(hfci, p_fci_internal->handleCFDATA1, /* file handle */
      cfdata, sizeof(*cfdata), err, p_fci_internal->pv)
      != sizeof(*cfdata) ) {
    fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  p_fci_internal->sizeFileCFDATA1 += sizeof(*cfdata);

  /* add optional reserved area */

  /* This allocation and freeing at each CFData block is a bit */
  /* inefficient, but it's harder to forget about freeing the buffer :-). */
  /* Reserved areas are used seldom besides that... */
  if (cbReserveCFData!=0) {
    if(!(reserved = (char*)PFCI_ALLOC(hfci, cbReserveCFData))) {
      fci_set_error( FCIERR_ALLOC_FAIL, ERROR_NOT_ENOUGH_MEMORY, TRUE );
      return FALSE;
    }
    for(i=0;i<cbReserveCFData;) {
      reserved[i++]='\0';
    }
    if( PFCI_WRITE(hfci, p_fci_internal->handleCFDATA1, /* file handle */
        reserved, /* memory buffer */
        cbReserveCFData, /* number of bytes to copy */
        err, p_fci_internal->pv) != cbReserveCFData ) {
      PFCI_FREE(hfci, reserved);
      fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err PFCI_FREE(hfci, reserved)*/

    p_fci_internal->sizeFileCFDATA1 += cbReserveCFData;
    PFCI_FREE(hfci, reserved);
  }

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

  p_fci_internal->sizeFileCFDATA1 += cfdata->cbData;

  /* reset the offset */
  p_fci_internal->cdata_in = 0;
  p_fci_internal->cCompressedBytesInFolder += cfdata->cbData;

  /* report status with pfnfcis about uncompressed and compressed file data */
  if( (*pfnfcis)(statusFile, cfdata->cbData, cfdata->cbUncomp,
      p_fci_internal->pv) == -1) {
    fci_set_error( FCIERR_USER_ABORT, 0, TRUE );
    return FALSE;
  }

  ++(p_fci_internal->cDataBlocks);

  return TRUE;
} /* end of fci_flush_data_block */





static cab_ULONG fci_get_checksum(const void *pv, UINT cb, CHECKSUM seed)
{
  cab_ULONG     csum;
  cab_ULONG     ul;
  int           cUlong;
  const BYTE    *pb;

  csum = seed;
  cUlong = cb / 4;
  pb = pv;

  while (cUlong-- > 0) {
    ul = *pb++;
    ul |= (((cab_ULONG)(*pb++)) <<  8);
    ul |= (((cab_ULONG)(*pb++)) << 16);
    ul |= (((cab_ULONG)(*pb++)) << 24);

    csum ^= ul;
  }

  ul = 0;
  switch (cb % 4) {
    case 3:
      ul |= (((ULONG)(*pb++)) << 16);
    case 2:
      ul |= (((ULONG)(*pb++)) <<  8);
    case 1:
      ul |= *pb++;
    default:
      break;
  }
  csum ^= ul;

  return csum;
} /* end of fci_get_checksum */



static BOOL fci_flushfolder_copy_cfdata(HFCI hfci, char* buffer, UINT cbReserveCFData,
  PFNFCISTATUS pfnfcis, int* err, int handleCFDATA1new,
  cab_ULONG* psizeFileCFDATA1new, cab_ULONG* payload)
{
  cab_ULONG read_result;
  CFDATA* pcfdata=(CFDATA*)buffer;
  BOOL split_block=FALSE;
  cab_UWORD savedUncomp=0;
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));

  *payload=0;

  /* while not all CFDATAs have been copied do */
  while(!FALSE) {
    if( p_fci_internal->fNextCab ) {
      if( split_block ) {
        /* internal error should never happen */
        fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
        return FALSE;
      }
    }
    /* REUSE the variable read_result */
    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=0;
    }
    if (p_fci_internal->fPrevCab) {
      read_result+=strlen(p_fci_internal->szPrevCab)+1 +
        strlen(p_fci_internal->szPrevDisk)+1;
    }
    /* No more CFDATA fits into the cabinet under construction */
    /* So don't try to store more data into it */
    if( p_fci_internal->fNextCab &&
        (p_fci_internal->oldCCAB.cb <= sizeof(CFDATA) + cbReserveCFData +
        p_fci_internal->sizeFileCFFILE1 + p_fci_internal->sizeFileCFDATA2 +
        p_fci_internal->sizeFileCFFILE2 + p_fci_internal->sizeFileCFFOLDER +
        sizeof(CFHEADER) +
        read_result +
        p_fci_internal->oldCCAB.cbReserveCFHeader +
        sizeof(CFFOLDER) +
        p_fci_internal->oldCCAB.cbReserveCFFolder +
        strlen(p_fci_internal->pccab->szCab)+1 +
        strlen(p_fci_internal->pccab->szDisk)+1
    )) {
      /* This may never be run for the first time the while loop is entered.
      Pray that the code that calls fci_flushfolder_copy_cfdata handles this.*/
      split_block=TRUE;  /* In this case split_block is abused to store */
      /* the complete data block into the next cabinet and not into the */
      /* current one. Originally split_block is the indicator that a */
      /* data block has been split across different cabinets. */
    } else {

      /* read CFDATA from p_fci_internal->handleCFDATA1 to cfdata*/
      read_result= PFCI_READ(hfci, p_fci_internal->handleCFDATA1,/*file handle*/
          buffer, /* memory buffer */
          sizeof(CFDATA)+cbReserveCFData, /* number of bytes to copy */
          err, p_fci_internal->pv);
      if (read_result!=sizeof(CFDATA)+cbReserveCFData) {
        if (read_result==0) break; /* ALL DATA has been copied */
        /* read error */
        fci_set_error( FCIERR_NONE, ERROR_READ_FAULT, TRUE );
        return FALSE;
      }
      /* TODO error handling of err */

      /* REUSE buffer p_fci_internal->data_out !!! */
      /* read data from p_fci_internal->handleCFDATA1 to */
      /*      p_fci_internal->data_out */
      if( PFCI_READ(hfci, p_fci_internal->handleCFDATA1 /* file handle */,
          p_fci_internal->data_out /* memory buffer */,
          pcfdata->cbData /* number of bytes to copy */,
          err, p_fci_internal->pv) != pcfdata->cbData ) {
        /* read error */
        fci_set_error( FCIERR_NONE, ERROR_READ_FAULT, TRUE );
        return FALSE;
      }
      /* TODO error handling of err */

      /* if cabinet size is too large */

      /* REUSE the variable read_result */
      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=0;
      }
      if (p_fci_internal->fPrevCab) {
        read_result+=strlen(p_fci_internal->szPrevCab)+1 +
          strlen(p_fci_internal->szPrevDisk)+1;
      }

      /* Is cabinet with new CFDATA too large? Then data block has to be split */
      if( p_fci_internal->fNextCab &&
          (p_fci_internal->oldCCAB.cb < sizeof(CFDATA) + cbReserveCFData +
          pcfdata->cbData +
          p_fci_internal->sizeFileCFFILE1 + p_fci_internal->sizeFileCFDATA2 +
          p_fci_internal->sizeFileCFFILE2 + p_fci_internal->sizeFileCFFOLDER +
          sizeof(CFHEADER) +
          read_result +
          p_fci_internal->oldCCAB.cbReserveCFHeader +
          sizeof(CFFOLDER) + /* size of new CFFolder entry */
          p_fci_internal->oldCCAB.cbReserveCFFolder +
          strlen(p_fci_internal->pccab->szCab)+1 + /* name of next cabinet */
          strlen(p_fci_internal->pccab->szDisk)+1  /* name of next disk */
      )) {
        /* REUSE read_result to save the size of the compressed data */
        read_result=pcfdata->cbData;
        /* Modify the size of the compressed data to store only a part of the */
        /* data block into the current cabinet. This is done to prevent */
        /* that the maximum cabinet size will be exceeded. The remainder */
        /* will be stored into the next following cabinet. */

        /* The cabinet will be of size "p_fci_internal->oldCCAB.cb". */
        /* Substract everything except the size of the block of data */
        /* to get it's actual size */
        pcfdata->cbData = p_fci_internal->oldCCAB.cb - (
          sizeof(CFDATA) + cbReserveCFData +
          p_fci_internal->sizeFileCFFILE1 + p_fci_internal->sizeFileCFDATA2 +
          p_fci_internal->sizeFileCFFILE2 + p_fci_internal->sizeFileCFFOLDER +
          sizeof(CFHEADER) +
          p_fci_internal->oldCCAB.cbReserveCFHeader +
          sizeof(CFFOLDER) + /* set size of new CFFolder entry */
          p_fci_internal->oldCCAB.cbReserveCFFolder );
        /* substract the size of special header fields */
        if ( p_fci_internal->oldCCAB.cbReserveCFHeader != 0 ||
            p_fci_internal->oldCCAB.cbReserveCFFolder != 0 ||
            p_fci_internal->oldCCAB.cbReserveCFData   != 0 ) {
          pcfdata->cbData-=4;
        }
        if (p_fci_internal->fPrevCab) {
          pcfdata->cbData-=strlen(p_fci_internal->szPrevCab)+1 +
            strlen(p_fci_internal->szPrevDisk)+1;
        }
        pcfdata->cbData-=strlen(p_fci_internal->pccab->szCab)+1 +
          strlen(p_fci_internal->pccab->szDisk)+1;

        savedUncomp = pcfdata->cbUncomp;
        pcfdata->cbUncomp = 0; /* on split blocks of data this is zero */

        /* if split_block==TRUE then the above while loop won't */
        /* be executed again */
        split_block=TRUE; /* split_block is the indicator that */
                          /* a data block has been split across */
                          /* different cabinets.*/
      }

      /* This should never happen !!! */
      if (pcfdata->cbData==0) {
        /* set error */
        fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
        return FALSE;
      }

      /* set little endian */
      pcfdata->cbData=fci_endian_uword(pcfdata->cbData);
      pcfdata->cbUncomp=fci_endian_uword(pcfdata->cbUncomp);

      /* get checksum and write to cfdata.csum */
      pcfdata->csum = fci_get_checksum( &(pcfdata->cbData),
        sizeof(CFDATA)+cbReserveCFData -
        sizeof(pcfdata->csum), fci_get_checksum( p_fci_internal->data_out, /*buffer*/
        pcfdata->cbData, 0 ) );

      /* set little endian */
      pcfdata->csum=fci_endian_ulong(pcfdata->csum);

      /* write cfdata with checksum to p_fci_internal->handleCFDATA2 */
      if( PFCI_WRITE(hfci, p_fci_internal->handleCFDATA2, /* file handle */
          buffer, /* memory buffer */
          sizeof(CFDATA)+cbReserveCFData, /* number of bytes to copy */
          err, p_fci_internal->pv) != sizeof(CFDATA)+cbReserveCFData ) {
         fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
         return FALSE;
      }
      /* TODO error handling of err */

      p_fci_internal->sizeFileCFDATA2 += sizeof(CFDATA)+cbReserveCFData;

      /* reset little endian */
      pcfdata->cbData=fci_endian_uword(pcfdata->cbData);
      pcfdata->cbUncomp=fci_endian_uword(pcfdata->cbUncomp);
      pcfdata->csum=fci_endian_ulong(pcfdata->csum);

      /* write compressed data into p_fci_internal->handleCFDATA2 */
      if( PFCI_WRITE(hfci, p_fci_internal->handleCFDATA2, /* file handle */
          p_fci_internal->data_out, /* memory buffer */
          pcfdata->cbData, /* number of bytes to copy */
          err, p_fci_internal->pv) != pcfdata->cbData) {
        fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
        return FALSE;
      }
      /* TODO error handling of err */

      p_fci_internal->sizeFileCFDATA2 += pcfdata->cbData;
      ++(p_fci_internal->cDataBlocks);
      p_fci_internal->statusFolderCopied += pcfdata->cbData;
      (*payload)+=pcfdata->cbUncomp;
      /* if cabinet size too large and data has been split */
      /* write the remainder of the data block to the new CFDATA1 file */
      if( split_block  ) { /* This does not include the */
                                  /* abused one (just search for "abused" )*/
      /* copy all CFDATA structures from handleCFDATA1 to handleCFDATA1new */
        if (p_fci_internal->fNextCab==FALSE ) {
          /* internal error */
          fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
          return FALSE;
        }

        /* set cbData to the size of the remainder of the data block */
        pcfdata->cbData = read_result - pcfdata->cbData;
        /*recover former value of cfdata.cbData; read_result will be the offset*/
        read_result -= pcfdata->cbData;
        pcfdata->cbUncomp = savedUncomp;

        /* reset checksum, it will be computed later */
        pcfdata->csum=0;

        /* write cfdata WITHOUT checksum to handleCFDATA1new */
        if( PFCI_WRITE(hfci, handleCFDATA1new, /* file handle */
            buffer, /* memory buffer */
            sizeof(CFDATA)+cbReserveCFData, /* number of bytes to copy */
            err, p_fci_internal->pv) != sizeof(CFDATA)+cbReserveCFData ) {
          fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
          return FALSE;
        }
        /* TODO error handling of err don't forget PFCI_FREE(hfci, reserved) */

        *psizeFileCFDATA1new += sizeof(CFDATA)+cbReserveCFData;

        /* write compressed data into handleCFDATA1new */
        if( PFCI_WRITE(hfci, handleCFDATA1new, /* file handle */
            p_fci_internal->data_out + read_result, /* memory buffer + offset */
                                                /* to last part of split data */
            pcfdata->cbData, /* number of bytes to copy */
            err, p_fci_internal->pv) != pcfdata->cbData) {
          fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
          return FALSE;
        }
        /* TODO error handling of err */

        p_fci_internal->statusFolderCopied += pcfdata->cbData;

        *psizeFileCFDATA1new += pcfdata->cbData;
        /* the two blocks of the split data block have been written */
        /* don't reset split_data yet, because it is still needed see below */
      }

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

    /* if cabinet size too large */
    /* write the remaining data blocks to the new CFDATA1 file */
    if ( split_block ) { /* This does include the */
                               /* abused one (just search for "abused" )*/
      if (p_fci_internal->fNextCab==FALSE ) {
        /* internal error */
        fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
        return FALSE;
      }
      /* copy all CFDATA structures from handleCFDATA1 to handleCFDATA1new */
      while(!FALSE) {
        /* read CFDATA from p_fci_internal->handleCFDATA1 to cfdata*/
        read_result= PFCI_READ(hfci, p_fci_internal->handleCFDATA1,/* handle */
            buffer, /* memory buffer */
            sizeof(CFDATA)+cbReserveCFData, /* number of bytes to copy */
            err, p_fci_internal->pv);
        if (read_result!=sizeof(CFDATA)+cbReserveCFData) {
          if (read_result==0) break; /* ALL DATA has been copied */
          /* read error */
          fci_set_error(FCIERR_NONE, ERROR_READ_FAULT, TRUE );
          return FALSE;
        }
        /* TODO error handling of err */

        /* REUSE buffer p_fci_internal->data_out !!! */
        /* read data from p_fci_internal->handleCFDATA1 to */
        /*      p_fci_internal->data_out */
        if( PFCI_READ(hfci, p_fci_internal->handleCFDATA1 /* file handle */,
            p_fci_internal->data_out /* memory buffer */,
            pcfdata->cbData /* number of bytes to copy */,
            err, p_fci_internal->pv) != pcfdata->cbData ) {
          /* read error */
          fci_set_error( FCIERR_NONE, ERROR_READ_FAULT, TRUE);
          return FALSE;
        }
        /* TODO error handling of err don't forget PFCI_FREE(hfci, reserved) */

        /* write cfdata with checksum to handleCFDATA1new */
        if( PFCI_WRITE(hfci, handleCFDATA1new, /* file handle */
            buffer, /* memory buffer */
            sizeof(CFDATA)+cbReserveCFData, /* number of bytes to copy */
            err, p_fci_internal->pv) != sizeof(CFDATA)+cbReserveCFData ) {
          fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
          return FALSE;
        }
        /* TODO error handling of err don't forget PFCI_FREE(hfci, reserved) */

        *psizeFileCFDATA1new += sizeof(CFDATA)+cbReserveCFData;

        /* write compressed data into handleCFDATA1new */
        if( PFCI_WRITE(hfci, handleCFDATA1new, /* file handle */
            p_fci_internal->data_out, /* memory buffer */
            pcfdata->cbData, /* number of bytes to copy */
            err, p_fci_internal->pv) != pcfdata->cbData) {
          fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
          return FALSE;
        }
        /* TODO error handling of err */

        *psizeFileCFDATA1new += pcfdata->cbData;
        p_fci_internal->statusFolderCopied += pcfdata->cbData;

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

      } /* end of WHILE */
      break; /* jump out of the next while loop */
    } /* end of if( split_data  ) */
  } /* end of WHILE */
  return TRUE;
} /* end of fci_flushfolder_copy_cfdata */





static BOOL fci_flushfolder_copy_cffolder(HFCI hfci, int* err, UINT cbReserveCFFolder,
  cab_ULONG sizeFileCFDATA2old)
{
  CFFOLDER cffolder;
  UINT i;
  char* reserved;
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));

  /* absolute offset cannot be set yet, because the size of cabinet header, */
  /* the number of CFFOLDERs and the number of CFFILEs may change. */
  /* Instead the size of all previous data blocks will be stored and */
  /* the remainder of the offset will be added when the cabinet will be */
  /* flushed to disk. */
  /* This is exactly the way the original CABINET.DLL works!!! */
  cffolder.coffCabStart=sizeFileCFDATA2old;

  /* set the number of this folder's CFDATA sections */
  cffolder.cCFData=p_fci_internal->cDataBlocks;
  /* TODO set compression type */
  cffolder.typeCompress = tcompTYPE_NONE;

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

  p_fci_internal->sizeFileCFFOLDER += sizeof(cffolder);

  /* add optional reserved area */
  if (cbReserveCFFolder!=0) {
    if(!(reserved = (char*)PFCI_ALLOC(hfci, cbReserveCFFolder))) {
      fci_set_error( FCIERR_ALLOC_FAIL, ERROR_NOT_ENOUGH_MEMORY, TRUE );
      return FALSE;
    }
    for(i=0;i<cbReserveCFFolder;) {
      reserved[i++]='\0';
    }
    if( PFCI_WRITE(hfci, p_fci_internal->handleCFFOLDER, /* file handle */
        reserved, /* memory buffer */
        cbReserveCFFolder, /* number of bytes to copy */
        err, p_fci_internal->pv) != cbReserveCFFolder ) {
      PFCI_FREE(hfci, reserved);
      fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    p_fci_internal->sizeFileCFFOLDER += cbReserveCFFolder;

    PFCI_FREE(hfci, reserved);
  }
  return TRUE;
} /* end of fci_flushfolder_copy_cffolder */





static BOOL fci_flushfolder_copy_cffile(HFCI hfci, int* err, int handleCFFILE1new,
  cab_ULONG *psizeFileCFFILE1new, cab_ULONG payload)
{
  CFFILE cffile;
  cab_ULONG read_result;
  cab_ULONG seek=0;
  cab_ULONG sizeOfFiles=0, sizeOfFilesPrev;
  BOOL may_be_prev=TRUE;
  cab_ULONG cbFileRemainer=0;
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));
  /* set seek of p_fci_internal->handleCFFILE1 to 0 */
  if( PFCI_SEEK(hfci,p_fci_internal->handleCFFILE1,0,SEEK_SET,err,
    p_fci_internal->pv) !=0 ) {
    /* wrong return value */
    fci_set_error( FCIERR_NONE, ERROR_SEEK, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  /* while not all CFFILE structures have been copied do */
  while(!FALSE) {
    /* REUSE the variable read_result */
    /* read data from p_fci_internal->handleCFFILE1 to cffile */
    read_result = PFCI_READ(hfci,p_fci_internal->handleCFFILE1/* file handle */,
      &cffile, /* memory buffer */
      sizeof(cffile), /* number of bytes to copy */
      err, p_fci_internal->pv);
    if( read_result != sizeof(cffile) ) {
      if( read_result == 0 ) break; /* ALL CFFILE structures have been copied */
      /* read error */
      fci_set_error( FCIERR_NONE, ERROR_READ_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    /* Microsoft's(R) CABINET.DLL would do a seek to the current! */
    /* position. I don't know why so I'll just omit it */

    /* read the filename from p_fci_internal->handleCFFILE1 */
    /* REUSE the variable read_result AGAIN */
    /* REUSE the memory buffer PFCI(hfci)->data_out */
    if( PFCI_READ(hfci, p_fci_internal->handleCFFILE1 /*file handle*/,
        p_fci_internal->data_out, /* memory buffer */
        CB_MAX_FILENAME, /* number of bytes to copy */
        err, p_fci_internal->pv) <2) {
      /* read error */
      fci_set_error( FCIERR_NONE, ERROR_READ_FAULT, TRUE );
      return FALSE;
    }
    /* TODO maybe other checks of read_result */
    /* TODO error handling of err */

    /* safety */
    if( strlen(p_fci_internal->data_out)>=CB_MAX_FILENAME ) {
      /* set error code internal error */
      fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
      return FALSE;
    }

    seek+=sizeof(cffile) + strlen(p_fci_internal->data_out)+1;

    /* set seek of p_fci_internal->handleCFFILE1 to end of file name */
    /* i.e. seek to the next CFFILE area */
    if( PFCI_SEEK(hfci,p_fci_internal->handleCFFILE1,
        seek, /* seek position*/
        SEEK_SET ,err,
        p_fci_internal->pv)
        != seek) {
      /* wrong return value */
      fci_set_error( FCIERR_NONE, ERROR_SEEK, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    /* fnfilfnfildest: placed file on cabinet */
    if (p_fci_internal->fNextCab ||
        p_fci_internal->fGetNextCabInVain) {
      PFCI_FILEPLACED( hfci, &(p_fci_internal->oldCCAB),
        p_fci_internal->data_out, /* the file name*/
        cffile.cbFile, /* file size */
        (cffile.iFolder==cffileCONTINUED_FROM_PREV),
        p_fci_internal->pv
      );
    } else {
      PFCI_FILEPLACED( hfci, p_fci_internal->pccab,
        p_fci_internal->data_out, /* the file name*/
        cffile.cbFile, /* file size */
        (cffile.iFolder==cffileCONTINUED_FROM_PREV),
        p_fci_internal->pv
      );
    }

    /* Check special iFolder values */
    if( cffile.iFolder==cffileCONTINUED_FROM_PREV &&
        p_fci_internal->fPrevCab==FALSE ) {
      /* THIS MAY NEVER HAPPEN */
      /* set error code */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
    if( cffile.iFolder==cffileCONTINUED_PREV_AND_NEXT ||
        cffile.iFolder==cffileCONTINUED_TO_NEXT ) {
      /* THIS MAY NEVER HAPPEN */
      /* set error code */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
    if( may_be_prev && cffile.iFolder!=cffileCONTINUED_FROM_PREV ) {
      may_be_prev=FALSE;
    }
    if( cffile.iFolder==cffileCONTINUED_FROM_PREV && may_be_prev==FALSE ) {
      /* THIS MAY NEVER HAPPEN */
      /* set error code */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
    if( cffile.iFolder!=cffileCONTINUED_FROM_PREV ) {
      may_be_prev=FALSE;
    }

    sizeOfFilesPrev=sizeOfFiles;
    /* Set complete size of all processed files */
    if( cffile.iFolder==cffileCONTINUED_FROM_PREV &&
        p_fci_internal->cbFileRemainer!=0
    ) {
      sizeOfFiles+=p_fci_internal->cbFileRemainer;
      p_fci_internal->cbFileRemainer=0;
    } else {
      sizeOfFiles+=cffile.cbFile;
    }

    /* Check if spanned file fits into this cabinet folder */
    if( cffile.iFolder==cffileCONTINUED_FROM_PREV && sizeOfFiles>payload ) {
      cffile.iFolder=cffileCONTINUED_PREV_AND_NEXT;
    } else

    /* Check if file doesn't fit into this cabinet folder */
    if( sizeOfFiles>payload ) {
      cffile.iFolder=cffileCONTINUED_TO_NEXT;
    }

    /* set little endian */
    cffile.cbFile=fci_endian_ulong(cffile.cbFile);
    cffile.uoffFolderStart=fci_endian_ulong(cffile.uoffFolderStart);
    cffile.iFolder=fci_endian_uword(cffile.iFolder);
    cffile.date=fci_endian_uword(cffile.date);
    cffile.time=fci_endian_uword(cffile.time);
    cffile.attribs=fci_endian_uword(cffile.attribs);

    /* write cffile to p_fci_internal->handleCFFILE2 */
    if( PFCI_WRITE(hfci, p_fci_internal->handleCFFILE2, /* 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 */

    p_fci_internal->sizeFileCFFILE2 += sizeof(cffile);

    /* reset little endian */
    cffile.cbFile=fci_endian_ulong(cffile.cbFile);
    cffile.uoffFolderStart=fci_endian_ulong(cffile.uoffFolderStart);
    cffile.iFolder=fci_endian_uword(cffile.iFolder);
    cffile.date=fci_endian_uword(cffile.date);
    cffile.time=fci_endian_uword(cffile.time);
    cffile.attribs=fci_endian_uword(cffile.attribs);

    /* write file name to p_fci_internal->handleCFFILE2 */
    if( PFCI_WRITE(hfci, p_fci_internal->handleCFFILE2, /* 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 */

    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 */
    p_fci_internal->oldCCAB = *p_fci_internal->pccab;
    /* 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 caught 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;
    }
  }

  /* set seek of p_fci_internal->handleCFDATA1 to 0 */
  if( PFCI_SEEK(hfci,p_fci_internal->handleCFDATA1,0,SEEK_SET,&err,
    p_fci_internal->pv) !=0 ) {
    /* wrong return value */
    fci_set_error( FCIERR_NONE, ERROR_SEEK, 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;
  }
  /* TODO error handling of err */

  /* save size of file CFDATA2 - required for the folder's offset to data */
  sizeFileCFDATA2old = p_fci_internal->sizeFileCFDATA2;

  if(!(reserved = (char*)PFCI_ALLOC(hfci, cbReserveCFData+sizeof(CFDATA)))) {
    fci_set_error( FCIERR_ALLOC_FAIL, ERROR_NOT_ENOUGH_MEMORY, 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;
  }

  if(!fci_flushfolder_copy_cfdata(hfci, reserved, cbReserveCFData, pfnfcis, &err,
      handleCFDATA1new, &sizeFileCFDATA1new, &payload
  )) {
    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 */
    PFCI_CLOSE(hfci,handleCFFILE1new,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_FREE(hfci,reserved);
    return FALSE;
  }

  PFCI_FREE(hfci,reserved);

  if(!fci_flushfolder_copy_cffolder(hfci, &err, cbReserveCFFolder,
       sizeFileCFDATA2old )) {
    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 */
    PFCI_CLOSE(hfci,handleCFFILE1new,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    return FALSE;
  }

  if(!fci_flushfolder_copy_cffile(hfci, &err, handleCFFILE1new,
      &sizeFileCFFILE1new, payload)) {
    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 */
    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;
  }

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

  /* put new CFDATA1 into hfci */
  memcpy(p_fci_internal->szFileNameCFDATA1,szFileNameCFDATA1new,
    CB_MAX_FILENAME);

  /* put CFDATA1 file handle */
  PFCI_INT(hfci)->handleCFDATA1 = handleCFDATA1new;
  /* set file size */
  PFCI_INT(hfci)->sizeFileCFDATA1 = sizeFileCFDATA1new;

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

  /* put new CFFILE1 into hfci */
  memcpy(p_fci_internal->szFileNameCFFILE1,szFileNameCFFILE1new,
    CB_MAX_FILENAME);

  /* put CFFILE1 file handle */
  p_fci_internal->handleCFFILE1 = handleCFFILE1new;
  /* set file size */
  p_fci_internal->sizeFileCFFILE1 = sizeFileCFFILE1new;

  ++(p_fci_internal->cFolders);

  /* reset CFFolder specific information */
  p_fci_internal->cDataBlocks=0;
  p_fci_internal->cCompressedBytesInFolder=0;

  return TRUE;
}  /* end of fci_flush_folder */




static BOOL fci_flush_cabinet(
	HFCI                  hfci,
	BOOL                  fGetNextCab,
	PFNFCIGETNEXTCABINET  pfnfcignc,
	PFNFCISTATUS          pfnfcis)
{
  int err;
  CFHEADER cfheader;
  struct {
    cab_UWORD  cbCFHeader;
    cab_UBYTE  cbCFFolder;
    cab_UBYTE  cbCFData;
  } cfreserved;
  CFFOLDER cffolder;
  cab_ULONG read_result=0;
  int handleCABINET;                            /* file handle for cabinet   */
  char szFileNameCABINET[CB_MAX_CAB_PATH+CB_MAX_CABINET_NAME];/* name buffer */
  UINT cbReserveCFHeader, cbReserveCFFolder, i;
  char* reserved;
  BOOL returntrue=FALSE;
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));

  /* TODO test if fci_flush_cabinet really aborts if there was no FCIAddFile */

  /* when FCIFlushCabinet was or FCIAddFile hasn't been called */
  if( p_fci_internal->sizeFileCFFILE1==0 && fGetNextCab ) {
    returntrue=TRUE;
  }

  if (!fci_flush_folder(hfci,fGetNextCab,pfnfcignc,pfnfcis)){
    /* TODO set error */
    return FALSE;
  }

  if(returntrue) return TRUE;

  if ( (p_fci_internal->fSplitFolder && p_fci_internal->fNextCab==FALSE)||
       (p_fci_internal->sizeFileCFFOLDER==0 &&
         (p_fci_internal->sizeFileCFFILE1!=0 ||
          p_fci_internal->sizeFileCFFILE2!=0 )
     ) )
  {
      /* error */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
  }

  if( p_fci_internal->fNextCab ||
      p_fci_internal->fGetNextCabInVain ) {
    cbReserveCFFolder=p_fci_internal->oldCCAB.cbReserveCFFolder;
    cbReserveCFHeader=p_fci_internal->oldCCAB.cbReserveCFHeader;
    /* safety */
    if (strlen(p_fci_internal->oldCCAB.szCabPath)>=CB_MAX_CAB_PATH ||
        strlen(p_fci_internal->oldCCAB.szCab)>=CB_MAX_CABINET_NAME) {
      /* set error */
      fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
      return FALSE;
    }
    /* get the full name of the cabinet */
    memcpy(szFileNameCABINET,p_fci_internal->oldCCAB.szCabPath,
      CB_MAX_CAB_PATH);
    memcpy(szFileNameCABINET+strlen(szFileNameCABINET),
      p_fci_internal->oldCCAB.szCab, CB_MAX_CABINET_NAME);
  } else {
    cbReserveCFFolder=p_fci_internal->pccab->cbReserveCFFolder;
    cbReserveCFHeader=p_fci_internal->pccab->cbReserveCFHeader;
    /* safety */
    if (strlen(p_fci_internal->pccab->szCabPath)>=CB_MAX_CAB_PATH ||
        strlen(p_fci_internal->pccab->szCab)>=CB_MAX_CABINET_NAME) {
      /* set error */
      fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
      return FALSE;
    }
    /* get the full name of the cabinet */
    memcpy(szFileNameCABINET,p_fci_internal->pccab->szCabPath,
      CB_MAX_CAB_PATH);
    memcpy(szFileNameCABINET+strlen(szFileNameCABINET),
      p_fci_internal->pccab->szCab, CB_MAX_CABINET_NAME);
  }

  memcpy(cfheader.signature,"!CAB",4);
  cfheader.reserved1=0;
  cfheader.cbCabinet=   /* size of the cabinet file in bytes */
    sizeof(CFHEADER) +
    p_fci_internal->sizeFileCFFOLDER +
    p_fci_internal->sizeFileCFFILE2 +
    p_fci_internal->sizeFileCFDATA2;

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

  if( ( ( p_fci_internal->fNextCab ||
          p_fci_internal->fGetNextCabInVain ) &&
        cfheader.cbCabinet > p_fci_internal->oldCCAB.cb
      ) ||
      ( ( p_fci_internal->fNextCab==FALSE &&
          p_fci_internal->fGetNextCabInVain==FALSE ) &&
        cfheader.cbCabinet > p_fci_internal->pccab->cb
      )
    )
  {
    fci_set_error( FCIERR_NONE, ERROR_MORE_DATA, TRUE );
    return FALSE;
  }


  cfheader.reserved2=0;
  cfheader.coffFiles=    /* offset to first CFFILE section */
   cfheader.cbCabinet - p_fci_internal->sizeFileCFFILE2 -
   p_fci_internal->sizeFileCFDATA2;

  cfheader.reserved3=0;
  cfheader.versionMinor=3;
  cfheader.versionMajor=1;
  /* number of CFFOLDER entries in the cabinet */
  cfheader.cFolders=p_fci_internal->cFolders;
  /* number of CFFILE entries in the cabinet */
  cfheader.cFiles=p_fci_internal->cFiles;
  cfheader.flags=0;    /* 1=prev cab, 2=next cabinet, 4=reserved sections */

  if( p_fci_internal->fPrevCab ) {
    cfheader.flags = cfheadPREV_CABINET;
  }

  if( p_fci_internal->fNextCab ) {
    cfheader.flags |= cfheadNEXT_CABINET;
  }

  if( p_fci_internal->fNextCab ||
      p_fci_internal->fGetNextCabInVain ) {
    if( p_fci_internal->oldCCAB.cbReserveCFHeader != 0 ||
        p_fci_internal->oldCCAB.cbReserveCFFolder != 0 ||
        p_fci_internal->oldCCAB.cbReserveCFData   != 0 ) {
      cfheader.flags |= cfheadRESERVE_PRESENT;
    }
    cfheader.setID = p_fci_internal->oldCCAB.setID;
    cfheader.iCabinet = p_fci_internal->oldCCAB.iCab-1;
  } else {
    if( p_fci_internal->pccab->cbReserveCFHeader != 0 ||
        p_fci_internal->pccab->cbReserveCFFolder != 0 ||
        p_fci_internal->pccab->cbReserveCFData   != 0 ) {
      cfheader.flags |= cfheadRESERVE_PRESENT;
    }
    cfheader.setID = p_fci_internal->pccab->setID;
    cfheader.iCabinet = p_fci_internal->pccab->iCab-1;
  }

  /* create the cabinet */
  handleCABINET = PFCI_OPEN(hfci, szFileNameCABINET,
    33538, 384, &err, p_fci_internal->pv );
  if(handleCABINET==0){
    fci_set_error( FCIERR_CAB_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error checking of err */

  /* set little endian */
  cfheader.reserved1=fci_endian_ulong(cfheader.reserved1);
  cfheader.cbCabinet=fci_endian_ulong(cfheader.cbCabinet);
  cfheader.reserved2=fci_endian_ulong(cfheader.reserved2);
  cfheader.coffFiles=fci_endian_ulong(cfheader.coffFiles);
  cfheader.reserved3=fci_endian_ulong(cfheader.reserved3);
  cfheader.cFolders=fci_endian_uword(cfheader.cFolders);
  cfheader.cFiles=fci_endian_uword(cfheader.cFiles);
  cfheader.flags=fci_endian_uword(cfheader.flags);
  cfheader.setID=fci_endian_uword(cfheader.setID);
  cfheader.iCabinet=fci_endian_uword(cfheader.iCabinet);

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

  /* reset little endian */
  cfheader.reserved1=fci_endian_ulong(cfheader.reserved1);
  cfheader.cbCabinet=fci_endian_ulong(cfheader.cbCabinet);
  cfheader.reserved2=fci_endian_ulong(cfheader.reserved2);
  cfheader.coffFiles=fci_endian_ulong(cfheader.coffFiles);
  cfheader.reserved3=fci_endian_ulong(cfheader.reserved3);
  cfheader.cFolders=fci_endian_uword(cfheader.cFolders);
  cfheader.cFiles=fci_endian_uword(cfheader.cFiles);
  cfheader.flags=fci_endian_uword(cfheader.flags);
  cfheader.setID=fci_endian_uword(cfheader.setID);
  cfheader.iCabinet=fci_endian_uword(cfheader.iCabinet);

  if( cfheader.flags & cfheadRESERVE_PRESENT ) {
    /* NOTE: No checks for maximum value overflows as designed by MS!!! */
    cfreserved.cbCFHeader = cbReserveCFHeader;
    cfreserved.cbCFFolder = cbReserveCFFolder;
    if( p_fci_internal->fNextCab ||
        p_fci_internal->fGetNextCabInVain ) {
      cfreserved.cbCFData = p_fci_internal->oldCCAB.cbReserveCFData;
    } else {
      cfreserved.cbCFData = p_fci_internal->pccab->cbReserveCFData;
    }

    /* set little endian */
    cfreserved.cbCFHeader=fci_endian_uword(cfreserved.cbCFHeader);

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

    /* reset little endian */
    cfreserved.cbCFHeader=fci_endian_uword(cfreserved.cbCFHeader);
  }

  /* add optional reserved area */
  if (cbReserveCFHeader!=0) {
    if(!(reserved = (char*)PFCI_ALLOC(hfci, cbReserveCFHeader))) {
      fci_set_error( FCIERR_ALLOC_FAIL, ERROR_NOT_ENOUGH_MEMORY, TRUE );
      return FALSE;
    }
    for(i=0;i<cbReserveCFHeader;) {
      reserved[i++]='\0';
    }
    if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
        reserved, /* memory buffer */
        cbReserveCFHeader, /* number of bytes to copy */
        &err, p_fci_internal->pv) != cbReserveCFHeader ) {
      PFCI_FREE(hfci, reserved);
      /* write error */
      fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */
    PFCI_FREE(hfci, reserved);
  }

  if( cfheader.flags & cfheadPREV_CABINET ) {
    if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
        p_fci_internal->szPrevCab, /* memory buffer */
        strlen(p_fci_internal->szPrevCab)+1, /* number of bytes to copy */
        &err, p_fci_internal->pv) != strlen(p_fci_internal->szPrevCab)+1 ) {
      /* write error */
      fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
        p_fci_internal->szPrevDisk, /* memory buffer */
        strlen(p_fci_internal->szPrevDisk)+1, /* number of bytes to copy */
        &err, p_fci_internal->pv) != strlen(p_fci_internal->szPrevDisk)+1 ) {
      /* write error */
      fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */
  }

  if( cfheader.flags & cfheadNEXT_CABINET ) {
    if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
        p_fci_internal->pccab->szCab, /* memory buffer */
        strlen(p_fci_internal->pccab->szCab)+1, /* number of bytes to copy */
        &err, p_fci_internal->pv) != strlen(p_fci_internal->pccab->szCab)+1 ) {
      /* write error */
      fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
        p_fci_internal->pccab->szDisk, /* memory buffer */
        strlen(p_fci_internal->pccab->szDisk)+1, /* number of bytes to copy */
        &err, p_fci_internal->pv) != strlen(p_fci_internal->pccab->szDisk)+1 ) {
      /* write error */
      fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */
  }

  /* set seek of p_fci_internal->handleCFFOLDER to 0 */
  if( PFCI_SEEK(hfci,p_fci_internal->handleCFFOLDER,
      0, SEEK_SET, &err, p_fci_internal->pv) != 0 ) {
    /* wrong return value */
    fci_set_error( FCIERR_NONE, ERROR_SEEK, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  /* while not all CFFOLDER structures have been copied into the cabinet do */
  while(!FALSE) {
    /* use the variable read_result */
    /* read cffolder of p_fci_internal->handleCFFOLDER */
    read_result = PFCI_READ(hfci, p_fci_internal->handleCFFOLDER, /* handle */
        &cffolder, /* memory buffer */
        sizeof(cffolder), /* number of bytes to copy */
        &err, p_fci_internal->pv);
    if( read_result != sizeof(cffolder) ) {
      if( read_result == 0 ) break;/*ALL CFFOLDER structures have been copied*/
      /* read error */
      fci_set_error( FCIERR_NONE, ERROR_READ_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    /* add size of header size of all CFFOLDERs and size of all CFFILEs */
    cffolder.coffCabStart +=
      p_fci_internal->sizeFileCFFILE2 + p_fci_internal->sizeFileCFFOLDER +
      sizeof(CFHEADER);
    if( p_fci_internal->fNextCab ||
        p_fci_internal->fGetNextCabInVain ) {
      cffolder.coffCabStart+=p_fci_internal->oldCCAB.cbReserveCFHeader;
    } else {
      cffolder.coffCabStart+=p_fci_internal->pccab->cbReserveCFHeader;
    }

    if (p_fci_internal->fPrevCab) {
      cffolder.coffCabStart += strlen(p_fci_internal->szPrevCab)+1 +
        strlen(p_fci_internal->szPrevDisk)+1;
    }

    if (p_fci_internal->fNextCab) {
      cffolder.coffCabStart += strlen(p_fci_internal->oldCCAB.szCab)+1 +
        strlen(p_fci_internal->oldCCAB.szDisk)+1;
    }

    if( p_fci_internal->fNextCab ||
        p_fci_internal->fGetNextCabInVain ) {
      cffolder.coffCabStart += p_fci_internal->oldCCAB.cbReserveCFHeader;
      if( p_fci_internal->oldCCAB.cbReserveCFHeader != 0 ||
          p_fci_internal->oldCCAB.cbReserveCFFolder != 0 ||
          p_fci_internal->oldCCAB.cbReserveCFData   != 0 ) {
        cffolder.coffCabStart += 4;
      }
    } else {
      cffolder.coffCabStart += p_fci_internal->pccab->cbReserveCFHeader;
      if( p_fci_internal->pccab->cbReserveCFHeader != 0 ||
          p_fci_internal->pccab->cbReserveCFFolder != 0 ||
          p_fci_internal->pccab->cbReserveCFData   != 0 ) {
        cffolder.coffCabStart += 4;
      }
    }

    /* set little endian */
    cffolder.coffCabStart=fci_endian_ulong(cffolder.coffCabStart);
    cffolder.cCFData=fci_endian_uword(cffolder.cCFData);
    cffolder.typeCompress=fci_endian_uword(cffolder.typeCompress);

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

    /* reset little endian */
    cffolder.coffCabStart=fci_endian_ulong(cffolder.coffCabStart);
    cffolder.cCFData=fci_endian_uword(cffolder.cCFData);
    cffolder.typeCompress=fci_endian_uword(cffolder.typeCompress);

    /* add optional reserved area */

    /* This allocation and freeing at each CFFolder block is a bit */
    /* inefficient, but it's harder to forget about freeing the buffer :-). */
    /* Reserved areas are used seldom besides that... */
    if (cbReserveCFFolder!=0) {
      if(!(reserved = PFCI_ALLOC(hfci, cbReserveCFFolder))) {
        fci_set_error( FCIERR_ALLOC_FAIL, ERROR_NOT_ENOUGH_MEMORY, TRUE );
        return FALSE;
      }

      if( PFCI_READ(hfci, p_fci_internal->handleCFFOLDER, /* file handle */
          reserved, /* memory buffer */
          cbReserveCFFolder, /* number of bytes to copy */
          &err, p_fci_internal->pv) != cbReserveCFFolder ) {
        PFCI_FREE(hfci, reserved);
        /* read error */
        fci_set_error( FCIERR_NONE, ERROR_READ_FAULT, TRUE );
        return FALSE;
      }
      /* TODO error handling of err */

      if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
          reserved, /* memory buffer */
          cbReserveCFFolder, /* number of bytes to copy */
          &err, p_fci_internal->pv) != cbReserveCFFolder ) {
        PFCI_FREE(hfci, reserved);
        /* write error */
        fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
        return FALSE;
      }
      /* TODO error handling of err */

      PFCI_FREE(hfci, reserved);
    }

  } /* END OF while */

  /* set seek of p_fci_internal->handleCFFILE2 to 0 */
  if( PFCI_SEEK(hfci,p_fci_internal->handleCFFILE2,
      0, SEEK_SET, &err, p_fci_internal->pv) != 0 ) {
    /* wrong return value */
    fci_set_error( FCIERR_NONE, ERROR_SEEK, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  /* while not all CFFILE structures have been copied to the cabinet do */
  while(!FALSE) {
    /* REUSE the variable read_result */
    /* REUSE the buffer p_fci_internal->data_out AGAIN */
    /* read a block from p_fci_internal->handleCFFILE2 */
    read_result = PFCI_READ(hfci, p_fci_internal->handleCFFILE2 /* handle */,
        p_fci_internal->data_out, /* memory buffer */
        CB_MAX_CHUNK, /* number of bytes to copy */
        &err, p_fci_internal->pv);
    if( read_result == 0 ) break; /* ALL CFFILE structures have been copied */
    /* TODO error handling of err */

    /* write the block to the cabinet file */
    if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
        p_fci_internal->data_out, /* memory buffer */
        read_result, /* number of bytes to copy */
        &err, p_fci_internal->pv) != read_result ) {
      /* write error */
      fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    if (p_fci_internal->fSplitFolder==FALSE) {
      p_fci_internal->statusFolderCopied = 0;
      /* TODO TEST THIS further */
      p_fci_internal->statusFolderTotal = p_fci_internal->sizeFileCFDATA2+
        p_fci_internal->sizeFileCFFILE2;
    }
    p_fci_internal->statusFolderCopied += read_result;

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

  } /* END OF while */

  /* set seek of p_fci_internal->handleCFDATA2 to 0 */
  if( PFCI_SEEK(hfci,p_fci_internal->handleCFDATA2,
      0, SEEK_SET, &err, p_fci_internal->pv) != 0 ) {
    /* wrong return value */
    fci_set_error( FCIERR_NONE, ERROR_SEEK, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  /* reset the number of folders for the next cabinet */
  p_fci_internal->cFolders=0;
  /* reset the number of files for the next cabinet */
  p_fci_internal->cFiles=0;

  /* while not all CFDATA structures have been copied to the cabinet do */
  while(!FALSE) {
    /* REUSE the variable read_result AGAIN */
    /* REUSE the buffer p_fci_internal->data_out AGAIN */
    /* read a block from p_fci_internal->handleCFDATA2 */
    read_result = PFCI_READ(hfci, p_fci_internal->handleCFDATA2 /* handle */,
        p_fci_internal->data_out, /* memory buffer */
        CB_MAX_CHUNK, /* number of bytes to copy */
        &err, p_fci_internal->pv);
    if( read_result == 0 ) break; /* ALL CFDATA structures have been copied */
    /* TODO error handling of err */

    /* write the block to the cabinet file */
    if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
        p_fci_internal->data_out, /* memory buffer */
        read_result, /* number of bytes to copy */
        &err, p_fci_internal->pv) != read_result ) {
      /* write error */
      fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
      return FALSE;
    }
    /* TODO error handling of err */

    p_fci_internal->statusFolderCopied += read_result;
    /* report status with pfnfcis about copied size of folder */
    if( (*pfnfcis)(statusFolder,
        p_fci_internal->statusFolderCopied, /* length of copied blocks */
        p_fci_internal->statusFolderTotal, /* total size of folder */
        p_fci_internal->pv) == -1) {
      /* set error code and abort */
      fci_set_error( FCIERR_USER_ABORT, 0, TRUE );
      return FALSE;
    }
  } /* END OF while */

  /* set seek of the cabinet file to 0 */
  if( PFCI_SEEK(hfci, handleCABINET,
      0, SEEK_SET, &err, p_fci_internal->pv) != 0 ) {
    /* wrong return value */
    fci_set_error( FCIERR_NONE, ERROR_SEEK, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  /* write the signature "MSCF" into the cabinet file */
  memcpy( cfheader.signature, "MSCF", 4 );
  if( PFCI_WRITE(hfci, handleCABINET, /* file handle */
      &cfheader, /* memory buffer */
      4, /* number of bytes to copy */
      &err, p_fci_internal->pv) != 4 ) {
    /* wrtie error */
    fci_set_error( FCIERR_CAB_FILE, ERROR_WRITE_FAULT, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  /* close the cabinet file */
  PFCI_CLOSE(hfci,handleCABINET,&err,p_fci_internal->pv);
  /* TODO error handling of err */


/* COPIED FROM FCIDestroy */

  PFCI_CLOSE (hfci, p_fci_internal->handleCFDATA2,&err,p_fci_internal->pv);
  /* TODO error handling of err */
  PFCI_DELETE(hfci, p_fci_internal->szFileNameCFDATA2, &err,
    p_fci_internal->pv);
  /* TODO error handling of err */
  PFCI_CLOSE (hfci, p_fci_internal->handleCFFILE2,&err,p_fci_internal->pv);
  /* TODO error handling of err */
  PFCI_DELETE(hfci, p_fci_internal->szFileNameCFFILE2, &err,
    p_fci_internal->pv);
  /* TODO error handling of err */
  PFCI_CLOSE (hfci, p_fci_internal->handleCFFOLDER,&err,p_fci_internal->pv);
  /* TODO error handling of err */
  PFCI_DELETE(hfci, p_fci_internal->szFileNameCFFOLDER, &err,
    p_fci_internal->pv);
  /* TODO error handling of err */

/* END OF copied from FCIDestroy */

  /* get 3 temporary files and open them */
  /* write names and handles to hfci */


  p_fci_internal->sizeFileCFDATA2  = 0;
  p_fci_internal->sizeFileCFFILE2  = 0;
  p_fci_internal->sizeFileCFFOLDER = 0;

/* COPIED FROM FCICreate */

  /* CFDATA with checksum and ready to be copied into cabinet */
  if( !PFCI_GETTEMPFILE(hfci, p_fci_internal->szFileNameCFDATA2,
      CB_MAX_FILENAME)) {
    /* error handling */
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    return FALSE;
  }
  /* safety */
  if ( strlen(p_fci_internal->szFileNameCFDATA2) >= CB_MAX_FILENAME ) {
    /* set error code and abort */
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  p_fci_internal->handleCFDATA2 = PFCI_OPEN(hfci,
    p_fci_internal->szFileNameCFDATA2, 34050, 384, &err, p_fci_internal->pv);
  /* check handle */
  if(p_fci_internal->handleCFDATA2==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error checking of err */

  /* array of all CFFILE in a folder, ready to be copied into cabinet */
  if( !PFCI_GETTEMPFILE(hfci,p_fci_internal->szFileNameCFFILE2,
      CB_MAX_FILENAME)) {
    /* error handling */
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    return FALSE;
  }
  /* safety */
  if ( strlen(p_fci_internal->szFileNameCFFILE2) >= CB_MAX_FILENAME ) {
    /* set error code and abort */
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  p_fci_internal->handleCFFILE2 = PFCI_OPEN(hfci,
    p_fci_internal->szFileNameCFFILE2, 34050, 384, &err, p_fci_internal->pv);
  /* check handle */
  if(p_fci_internal->handleCFFILE2==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE);
    return FALSE;
  }
  /* TODO error checking of err */

  /* array of all CFFILE in a folder, ready to be copied into cabinet */
  if (!PFCI_GETTEMPFILE(hfci,p_fci_internal->szFileNameCFFOLDER,CB_MAX_FILENAME)) {
    /* error handling */
    fci_set_error( FCIERR_NONE, ERROR_FUNCTION_FAILED, TRUE );
    return FALSE;
  }
  /* safety */
  if ( strlen(p_fci_internal->szFileNameCFFOLDER) >= CB_MAX_FILENAME ) {
    /* set error code and abort */
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  p_fci_internal->handleCFFOLDER = PFCI_OPEN(hfci,
    p_fci_internal->szFileNameCFFOLDER, 34050, 384, &err, p_fci_internal->pv);
  /* check handle */
  if(p_fci_internal->handleCFFOLDER==0){
    fci_set_error( FCIERR_TEMP_FILE, ERROR_OPEN_FAILED, TRUE );
    return FALSE;
  }
  /* TODO error checking of err */

/* END OF copied from FCICreate */


  /* TODO close and delete new files when return FALSE */


  /* report status with pfnfcis about copied size of folder */
  (*pfnfcis)(statusCabinet,
    p_fci_internal->estimatedCabinetSize, /* estimated cabinet file size */
    cfheader.cbCabinet /* real cabinet file size */, p_fci_internal->pv);

  p_fci_internal->fPrevCab=TRUE;
  /* The sections szPrevCab and szPrevDisk are not being updated, because */
  /* MS CABINET.DLL always puts the first cabinet name and disk into them */

  if (p_fci_internal->fNextCab) {
    p_fci_internal->fNextCab=FALSE;

    if (p_fci_internal->sizeFileCFFILE1==0 && p_fci_internal->sizeFileCFDATA1!=0) {
      /* THIS CAN NEVER HAPPEN */
      /* set error code */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }

/* COPIED FROM FCIAddFile and modified */

    /* REUSE the variable read_result */
    if (p_fci_internal->fGetNextCabInVain) {
      read_result=p_fci_internal->oldCCAB.cbReserveCFHeader;
      if(p_fci_internal->sizeFileCFFILE1!=0) {
        read_result+=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;
      if(p_fci_internal->sizeFileCFFILE1!=0) {
        read_result+=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;
    }
    read_result+= p_fci_internal->sizeFileCFDATA1 +
      p_fci_internal->sizeFileCFFILE1 + p_fci_internal->sizeFileCFDATA2 +
      p_fci_internal->sizeFileCFFILE2 + p_fci_internal->sizeFileCFFOLDER +
      sizeof(CFHEADER) +
      sizeof(CFFOLDER); /* set size of new CFFolder entry */

    if( p_fci_internal->fNewPrevious ) {
      memcpy(p_fci_internal->szPrevCab, p_fci_internal->oldCCAB.szCab,
        CB_MAX_CABINET_NAME);
      memcpy(p_fci_internal->szPrevDisk, p_fci_internal->oldCCAB.szDisk,
        CB_MAX_DISK_NAME);
      p_fci_internal->fNewPrevious=FALSE;
    }

    /* too much data for the maximum size of a cabinet */
    if( p_fci_internal->fGetNextCabInVain==FALSE &&
        p_fci_internal->pccab->cb < read_result ) {
      return fci_flush_cabinet( hfci, FALSE, pfnfcignc, pfnfcis);
    }

    /* Might be too much data for the maximum size of a cabinet.*/
    /* 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->pccab->cb < read_result +
      CB_MAX_CABINET_NAME + CB_MAX_DISK_NAME
    )) {
      /* save CCAB */
      p_fci_internal->oldCCAB = *p_fci_internal->pccab;
      /* 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 );
        return FALSE;
      }
      /* Skip a few lines of code. This is caught by the next if. */
      p_fci_internal->fGetNextCabInVain=TRUE;
    }

    /* too much data for cabinet */
    if (p_fci_internal->fGetNextCabInVain && (
        p_fci_internal->oldCCAB.cb < read_result +
        strlen(p_fci_internal->oldCCAB.szCab)+1+
        strlen(p_fci_internal->oldCCAB.szDisk)+1
    )) {
      p_fci_internal->fGetNextCabInVain=FALSE;
      p_fci_internal->fNextCab=TRUE;
      return fci_flush_cabinet( hfci, FALSE, pfnfcignc, pfnfcis);
    }

    /* if the FolderThreshold has been reached flush the folder automatically */
    if( p_fci_internal->fGetNextCabInVain ) {
      if( p_fci_internal->cCompressedBytesInFolder >=
          p_fci_internal->oldCCAB.cbFolderThresh) {
        return FCIFlushFolder(hfci, pfnfcignc, pfnfcis);
      }
    } else {
      if( p_fci_internal->cCompressedBytesInFolder >=
          p_fci_internal->pccab->cbFolderThresh) {
        return FCIFlushFolder(hfci, pfnfcignc, pfnfcis);
      }
    }

/* END OF COPIED FROM FCIAddFile and modified */

    if( p_fci_internal->sizeFileCFFILE1>0 ) {
      if( !FCIFlushFolder(hfci, pfnfcignc, pfnfcis) ) return FALSE;
      p_fci_internal->fNewPrevious=TRUE;
    }
  } else {
    p_fci_internal->fNewPrevious=FALSE;
    if( p_fci_internal->sizeFileCFFILE1>0 || p_fci_internal->sizeFileCFDATA1) {
      /* THIS MAY NEVER HAPPEN */
      /* set error structures */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
  }

  return TRUE;
} /* end of fci_flush_cabinet */





/***********************************************************************
 *		FCIAddFile (CABINET.11)
 *
 * FCIAddFile adds a file to the to be created cabinet file
 *
 * PARAMS
 *   hfci          [I]  An HFCI from FCICreate
 *   pszSourceFile [I]  A pointer to a C string which contains the name and
 *                      location of the file which will be added to the cabinet
 *   pszFileName   [I]  A pointer to a C string which contains the name under
 *                      which the file will be stored in the cabinet
 *   fExecute      [I]  A boolean value which indicates if the file should be
 *                      executed after extraction of self extracting
 *                      executables
 *   pfnfcignc     [I]  A pointer to a function which gets information about
 *                      the next cabinet
 *   pfnfcis      [IO]  A pointer to a function which will report status
 *                      information about the compression process
 *   pfnfcioi      [I]  A pointer to a function which reports file attributes
 *                      and time and date information
 *   typeCompress  [I]  Compression type
 *
 * RETURNS
 *   On success, returns TRUE
 *   On failure, returns FALSE
 *
 * INCLUDES
 *   fci.h
 *
 */
BOOL __cdecl FCIAddFile(
	HFCI                  hfci,
	char                 *pszSourceFile,
	char                 *pszFileName,
	BOOL                  fExecute,
	PFNFCIGETNEXTCABINET  pfnfcignc,
	PFNFCISTATUS          pfnfcis,
	PFNFCIGETOPENINFO     pfnfcigoi,
	TCOMP                 typeCompress)
{
  int err;
  CFFILE cffile;
  cab_ULONG read_result;
  int file_handle;
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));

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

  if ((!pszSourceFile) || (!pszFileName) || (!pfnfcignc) || (!pfnfcis) ||
      (!pfnfcigoi) || strlen(pszFileName)>=CB_MAX_FILENAME) {
    fci_set_error( FCIERR_NONE, ERROR_BAD_ARGUMENTS, TRUE );
    return FALSE;
  }

  /* TODO check if pszSourceFile??? */

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

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

  cffile.cbFile=0; /* size of the to be added file*/
  /* offset of the uncompressed file in the folder */
  cffile.uoffFolderStart=p_fci_internal->cDataBlocks*CAB_BLOCKMAX + p_fci_internal->cdata_in;
  /* number of folder in the cabinet or special 0=first  */
  cffile.iFolder = p_fci_internal->cFolders;

  /* allocation of memory */
  if (p_fci_internal->data_in==NULL) {
    if (p_fci_internal->cdata_in!=0) {
      /* error handling */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
    if (p_fci_internal->data_out!=NULL) {
      /* error handling */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
    if(!(p_fci_internal->data_in = (char*)PFCI_ALLOC(hfci,CB_MAX_CHUNK))) {
      fci_set_error( FCIERR_ALLOC_FAIL, ERROR_NOT_ENOUGH_MEMORY, TRUE );
      return FALSE;
    }
    if (p_fci_internal->data_out==NULL) {
      if(!(p_fci_internal->data_out = PFCI_ALLOC(hfci, 2 * CB_MAX_CHUNK))){
        fci_set_error( FCIERR_ALLOC_FAIL, ERROR_NOT_ENOUGH_MEMORY, TRUE );
        return FALSE;
      }
    }
  }

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

  /* get information about the file */
  /* set defaults in case callback doesn't set one or more fields */
  cffile.attribs=0;
  cffile.date=0;
  cffile.time=0;
  file_handle=(*pfnfcigoi)(pszSourceFile, &(cffile.date), &(cffile.time),
    &(cffile.attribs), &err, p_fci_internal->pv);
  /* check file_handle */
  if(file_handle==0){
    fci_set_error( FCIERR_OPEN_SRC, ERROR_OPEN_FAILED, TRUE );
  }
  /* TODO error handling of err */

  if (fExecute) { cffile.attribs |= _A_EXEC; }

  /* REUSE the variable read_result */
  if (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 ) { /* this is never the case */
    read_result+= strlen(p_fci_internal->pccab->szCab)+1+
      strlen(p_fci_internal->pccab->szDisk)+1;
  }

  read_result+= sizeof(CFFILE) + strlen(pszFileName)+1 +
    p_fci_internal->sizeFileCFFILE1 + p_fci_internal->sizeFileCFDATA2 +
    p_fci_internal->sizeFileCFFILE2 + p_fci_internal->sizeFileCFFOLDER +
    sizeof(CFHEADER) +
    sizeof(CFFOLDER); /* size of new CFFolder entry */

  /* Might be too much data for the maximum size of a cabinet.*/
  /* 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 +
        CB_MAX_CABINET_NAME + CB_MAX_DISK_NAME
      )
  ) {
    /* save CCAB */
    p_fci_internal->oldCCAB = *p_fci_internal->pccab;
    /* 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 );
      return FALSE;
    }
    /* Skip a few lines of code. This is caught by the next if. */
    p_fci_internal->fGetNextCabInVain=TRUE;
  }

  if( p_fci_internal->fGetNextCabInVain &&
      p_fci_internal->fNextCab
  ) {
    /* THIS CAN NEVER HAPPEN */
    /* set error code */
    fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
    return FALSE;
  }

  /* too much data for cabinet */
  if( p_fci_internal->fGetNextCabInVain &&
     (
      p_fci_internal->oldCCAB.cb < read_result +
      strlen(p_fci_internal->pccab->szCab)+1+
      strlen(p_fci_internal->pccab->szDisk)+1
  )) {
    p_fci_internal->fGetNextCabInVain=FALSE;
    p_fci_internal->fNextCab=TRUE;
    if(!fci_flush_cabinet( hfci, FALSE, pfnfcignc, pfnfcis)) return FALSE;
  }

  if( p_fci_internal->fNextCab ) {
    /* THIS MAY NEVER HAPPEN */
    /* set error code */
    fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
    return FALSE;
  }

  /* read the contents of the file blockwise */
  while (!FALSE) {
    if (p_fci_internal->cdata_in > CAB_BLOCKMAX) {
      /* internal error */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }

    read_result = PFCI_READ(hfci, file_handle /* file handle */,
      (p_fci_internal->data_in + p_fci_internal->cdata_in) /* memory buffer */,
      (CAB_BLOCKMAX - p_fci_internal->cdata_in) /* number of bytes to copy */,
      &err, p_fci_internal->pv);
    /* TODO error handling of err */

    if( read_result==0 ) break;

    /* increment the block size */
    p_fci_internal->cdata_in += read_result;

    /* increment the file size */
    cffile.cbFile += read_result;

    if ( p_fci_internal->cdata_in > CAB_BLOCKMAX ) {
      /* report internal error */
      fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
      return FALSE;
    }
    /* write a whole block */
    if ( p_fci_internal->cdata_in == CAB_BLOCKMAX ) {

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

  /* close the file from FCIAddFile */
  PFCI_CLOSE(hfci,file_handle,&err,p_fci_internal->pv);
  /* TODO error handling of err */

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

  p_fci_internal->sizeFileCFFILE1 += sizeof(cffile);

  /* append the name of file */
  if (strlen(pszFileName)>=CB_MAX_FILENAME) {
    /* IMPOSSIBLE */
    /* set error code */
    fci_set_error( FCIERR_NONE, ERROR_INVALID_DATA, TRUE );
    return FALSE;
  }
  if( PFCI_WRITE(hfci, p_fci_internal->handleCFFILE1, /* file handle */
      pszFileName, strlen(pszFileName)+1, &err, p_fci_internal->pv)
      != strlen(pszFileName)+1 ) {
    /* write error */
    fci_set_error( FCIERR_TEMP_FILE, ERROR_WRITE_FAULT, TRUE );
    return FALSE;
  }
  /* TODO error handling of err */

  p_fci_internal->sizeFileCFFILE1 += strlen(pszFileName)+1;

  /* REUSE the variable read_result */
  if (p_fci_internal->fGetNextCabInVain ||
      p_fci_internal->fNextCab
     ) {
    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 ) { /* this is never the case */
    read_result+= strlen(p_fci_internal->pccab->szCab)+1+
      strlen(p_fci_internal->pccab->szDisk)+1;
  }
  read_result+= p_fci_internal->sizeFileCFDATA1 +
    p_fci_internal->sizeFileCFFILE1 + p_fci_internal->sizeFileCFDATA2 +
    p_fci_internal->sizeFileCFFILE2 + p_fci_internal->sizeFileCFFOLDER +
    sizeof(CFHEADER) +
    sizeof(CFFOLDER); /* set size of new CFFolder entry */

  /* too much data for the maximum size of a cabinet */
  /* (ignoring the unflushed data block) */
  if( p_fci_internal->fGetNextCabInVain==FALSE &&
      p_fci_internal->fNextCab==FALSE && /* this is always the case */
      p_fci_internal->pccab->cb < read_result ) {
    return fci_flush_cabinet( hfci, FALSE, pfnfcignc, pfnfcis);
  }

  /* Might be too much data for the maximum size of a cabinet.*/
  /* 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 */
  /* (ignoring the unflushed data block) */
  if( p_fci_internal->fGetNextCabInVain==FALSE &&
      p_fci_internal->fNextCab==FALSE &&
      ( p_fci_internal->pccab->cb < read_result +
        CB_MAX_CABINET_NAME + CB_MAX_DISK_NAME
      )
  ) {
    /* save CCAB */
    p_fci_internal->oldCCAB = *p_fci_internal->pccab;
    /* 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 );
      return FALSE;
    }
    /* Skip a few lines of code. This is caught by the next if. */
    p_fci_internal->fGetNextCabInVain=TRUE;
  }

  if( p_fci_internal->fGetNextCabInVain &&
      p_fci_internal->fNextCab
  ) {
    /* THIS CAN NEVER HAPPEN */
    fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
    return FALSE;
  }

  /* too much data for cabinet */
  if( (p_fci_internal->fGetNextCabInVain ||
      p_fci_internal->fNextCab) && (
      p_fci_internal->oldCCAB.cb < read_result +
      strlen(p_fci_internal->pccab->szCab)+1+
      strlen(p_fci_internal->pccab->szDisk)+1
  )) {

    p_fci_internal->fGetNextCabInVain=FALSE;
    p_fci_internal->fNextCab=TRUE;
    return fci_flush_cabinet( hfci, FALSE, pfnfcignc, pfnfcis);
  }

  if( p_fci_internal->fNextCab ) {
    /* THIS MAY NEVER HAPPEN */
    /* set error code */
    fci_set_error( FCIERR_NONE, ERROR_GEN_FAILURE, TRUE );
    return FALSE;
  }

  /* if the FolderThreshold has been reached flush the folder automatically */
  if( p_fci_internal->fGetNextCabInVain ) {
    if( p_fci_internal->cCompressedBytesInFolder >=
        p_fci_internal->oldCCAB.cbFolderThresh) {
      return FCIFlushFolder(hfci, pfnfcignc, pfnfcis);
    }
  } else {
    if( p_fci_internal->cCompressedBytesInFolder >=
        p_fci_internal->pccab->cbFolderThresh) {
      return FCIFlushFolder(hfci, pfnfcignc, pfnfcis);
    }
  }

  return TRUE;
} /* end of FCIAddFile */





/***********************************************************************
 *		FCIFlushFolder (CABINET.12)
 *
 * FCIFlushFolder completes the CFFolder structure under construction.
 *
 * All further data which is added by FCIAddFile will be associated to
 * the next CFFolder structure.
 *
 * FCIFlushFolder will be called by FCIAddFile automatically if the
 * threshold (stored in the member cbFolderThresh of the CCAB structure
 * pccab passed to FCICreate) is exceeded.
 *
 * FCIFlushFolder will be called by FCIFlushFolder automatically before
 * any data will be written into the cabinet file.
 *
 * PARAMS
 *   hfci          [I]  An HFCI from FCICreate
 *   pfnfcignc     [I]  A pointer to a function which gets information about
 *                      the next cabinet
 *   pfnfcis      [IO]  A pointer to a function which will report status
 *                      information about the compression process
 *
 * RETURNS
 *   On success, returns TRUE
 *   On failure, returns FALSE
 *
 * INCLUDES
 *   fci.h
 *
 */
BOOL __cdecl FCIFlushFolder(
	HFCI                  hfci,
	PFNFCIGETNEXTCABINET  pfnfcignc,
	PFNFCISTATUS          pfnfcis)
{
  return fci_flush_folder(hfci,FALSE,pfnfcignc,pfnfcis);
} /* end of FCIFlushFolder */



/***********************************************************************
 *		FCIFlushCabinet (CABINET.13)
 *
 * FCIFlushCabinet stores the data which has been added by FCIAddFile
 * into the cabinet file. If the maximum cabinet size (stored in the
 * member cb of the CCAB structure pccab passed to FCICreate) has been
 * exceeded FCIFlushCabinet will be called automatic by FCIAddFile.
 * The remaining data still has to be flushed manually by calling
 * FCIFlushCabinet.
 *
 * After FCIFlushCabinet has been called (manually) FCIAddFile must
 * NOT be called again. Then hfci has to be released by FCIDestroy.
 *
 * PARAMS
 *   hfci          [I]  An HFCI from FCICreate
 *   fGetNextCab   [I]  Whether you want to add additional files to a
 *                      cabinet set (TRUE) or whether you want to
 *                      finalize it (FALSE)
 *   pfnfcignc     [I]  A pointer to a function which gets information about
 *                      the next cabinet
 *   pfnfcis      [IO]  A pointer to a function which will report status
 *                      information about the compression process
 *
 * RETURNS
 *   On success, returns TRUE
 *   On failure, returns FALSE
 *
 * INCLUDES
 *   fci.h
 *
 */
BOOL __cdecl FCIFlushCabinet(
	HFCI                  hfci,
	BOOL                  fGetNextCab,
	PFNFCIGETNEXTCABINET  pfnfcignc,
	PFNFCISTATUS          pfnfcis)
{
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));

  if(!fci_flush_cabinet(hfci,fGetNextCab,pfnfcignc,pfnfcis)) return FALSE;

  while( p_fci_internal->sizeFileCFFILE1>0 ||
         p_fci_internal->sizeFileCFFILE2>0 ) {
    if(!fci_flush_cabinet(hfci,fGetNextCab,pfnfcignc,pfnfcis)) return FALSE;
  }

  return TRUE;
} /* end of FCIFlushCabinet */


/***********************************************************************
 *		FCIDestroy (CABINET.14)
 *
 * Frees a handle created by FCICreate.
 * Only reason for failure would be an invalid handle.
 *
 * PARAMS
 *   hfci [I] The HFCI to free
 *
 * RETURNS
 *   TRUE for success
 *   FALSE for failure
 */
BOOL __cdecl FCIDestroy(HFCI hfci)
{
  int err;
  PFCI_Int p_fci_internal=((PFCI_Int)(hfci));
  if (REALLY_IS_FCI(hfci)) {

    /* before hfci can be removed all temporary files must be closed */
    /* and deleted */
    p_fci_internal->FCI_Intmagic = 0;

    PFCI_CLOSE (hfci, p_fci_internal->handleCFDATA1,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_DELETE(hfci, p_fci_internal->szFileNameCFDATA1, &err,
      p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_CLOSE (hfci, p_fci_internal->handleCFFILE1,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_DELETE(hfci, p_fci_internal->szFileNameCFFILE1, &err,
      p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_CLOSE (hfci, p_fci_internal->handleCFDATA2,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_DELETE(hfci, p_fci_internal->szFileNameCFDATA2, &err,
      p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_CLOSE (hfci, p_fci_internal->handleCFFILE2,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_DELETE(hfci, p_fci_internal->szFileNameCFFILE2, &err,
      p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_CLOSE (hfci, p_fci_internal->handleCFFOLDER,&err,p_fci_internal->pv);
    /* TODO error handling of err */
    PFCI_DELETE(hfci, p_fci_internal->szFileNameCFFOLDER, &err,
      p_fci_internal->pv);
    /* TODO error handling of err */

    /* data in and out buffers have to be removed */
    if (p_fci_internal->data_in!=NULL)
      PFCI_FREE(hfci, p_fci_internal->data_in);
    if (p_fci_internal->data_out!=NULL)
      PFCI_FREE(hfci, p_fci_internal->data_out);

    /* hfci can now be removed */
    PFCI_FREE(hfci, hfci);
    return TRUE;
  } else {
    SetLastError(ERROR_INVALID_HANDLE);
    return FALSE;
  }

} /* end of FCIDestroy */
