//
// Piece BN 22-Mai-98
//
//
//
//
#include <stdlib.h>
#include <malloc.h>
#include <string.h>
#include <stdio.h>

#include "WinMain.h"
#include "System.h"
#include "Piece.h"

#define __CFILE__ "Piece"
char PIECE_acString[1024];

#define DATENBLOCKANZAHL 1024*1000*2 // umgehe realloc mit Mega-Blockgröße scheint ein Bug mit realloc zu sein

// *******************************************************************
// vlInit
// *******************************************************************
Piece::vlInit (void)
{
VPiece_ *pStruktur;


pStruktur = &pVPiece;
pStruktur->nStatus = FALSE;
pStruktur->Daten = (VPieceDaten_ *)Mem_Alloc(sizeof(VPieceDaten_));
if(pStruktur->Daten!=NULL){
memset(pStruktur->Daten, 0, sizeof(VPieceDaten_));
if(pStruktur->Daten->InterneListe.vlInit()==TRUE){
pStruktur->Daten->nErsterDurchlauf = TRUE;
pStruktur->nStatus = TRUE;
} else {
sprintf(PIECE_acString, "Can not get %s(1).", "pStruktur->Daten->InterneListe.vlInit");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
return(FALSE);
}
} else {
sprintf(PIECE_acString, "Can not get %d KBytes(2).", (sizeof(VPieceDaten_)/ 1024));
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
return(FALSE);
}
return(pStruktur->nStatus);
}

// *******************************************************************
// vlnew
// *******************************************************************
Piece::vlnew (void *pBuffer, long lLaenge)
{
int nRet=FALSE;
long lMerker;
long lWert;
long lIndex;
long lGroesse;
void *pPointer;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->nErsterDurchlauf==TRUE){
pVPiece.Daten->pDatenBuffer = (char *)Mem_Alloc(DATENBLOCKANZAHL + lLaenge);
if(pVPiece.Daten->pDatenBuffer!=NULL){
if(pVPiece.Daten->InterneListe.vlnew(&pPointer, sizeof(long))==TRUE){
memcpy(pPointer, &lLaenge, sizeof(long));
memset(pVPiece.Daten->pDatenBuffer, 0, DATENBLOCKANZAHL + lLaenge);
pVPiece.Daten->nErsterDurchlauf = FALSE;
pVPiece.Daten->lGroessepDatenBuffer = DATENBLOCKANZAHL + lLaenge;
pVPiece.Daten->lAnzahlEintraege = 1;
pVPiece.Daten->lAktuellerEintrag = 0;
pVPiece.Daten->lPosition = 0;

lWert = (long)(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lAktuellerEintrag * lLaenge);
memcpy(pBuffer, &lWert, sizeof(long));

nRet = TRUE;
} else {
vlDeInit();
sprintf(PIECE_acString, "Can not get %s(3).", "pVPiece.Daten->InterneListe.vlnew");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
} else {
vlDeInit();
sprintf(PIECE_acString, "Can not get %d KBytes(4).", ((DATENBLOCKANZAHL + lLaenge) / 1024));
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
} else {
if(pVPiece.Daten->InterneListe.vlnew(&pPointer, sizeof(long))==TRUE){
memcpy(pPointer, &lLaenge, sizeof(long));
//lGroesse = pVPiece.Daten->lGesamtLaenge;
//pVPiece.Daten->lGesamtLaenge += lLaenge;

pVPiece.Daten->InterneListe.vlreq(&pPointer, &lIndex);
lIndex--;
pVPiece.Daten->InterneListe.vlroot();
lGroesse = 0;
lWert = 0;
while(pVPiece.Daten->InterneListe.vlnext(&pPointer) && lWert<lIndex){
lWert++;
memcpy(&lMerker, pPointer, sizeof(long));
lGroesse += lMerker;
}
lIndex++;
pVPiece.Daten->InterneListe.vlnext(&pPointer);

if((lGroesse + lLaenge)<pVPiece.Daten->lGroessepDatenBuffer){
memcpy(pVPiece.Daten->pDatenBuffer + lGroesse + lLaenge, pVPiece.Daten->pDatenBuffer + lGroesse, lLaenge);
lWert = (long)(pVPiece.Daten->pDatenBuffer + lGroesse);
memcpy(pBuffer, &lWert, sizeof(long));
pVPiece.Daten->lAnzahlEintraege++;
memset((long *)lWert, 0, lLaenge);
nRet = TRUE;
} else {
pVPiece.Daten->pDatenBuffer = (char *)Mem_ReAlloc(pVPiece.Daten->pDatenBuffer, pVPiece.Daten->lGroessepDatenBuffer, (pVPiece.Daten->lGroessepDatenBuffer + pVPiece.Daten->lGroessepDatenBuffer + lLaenge));
if(pVPiece.Daten->pDatenBuffer!=NULL){
memset(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lGroessepDatenBuffer, 0, pVPiece.Daten->lGroessepDatenBuffer + lLaenge);
pVPiece.Daten->lGroessepDatenBuffer = (pVPiece.Daten->lGroessepDatenBuffer + pVPiece.Daten->lGroessepDatenBuffer + lLaenge);
lWert = (long)(pVPiece.Daten->pDatenBuffer + lGroesse);
memcpy(pBuffer, &lWert, sizeof(long));
pVPiece.Daten->lAnzahlEintraege++;
memset((long *)lWert, 0, lLaenge);
nRet = TRUE;
} else {
sprintf(PIECE_acString, "Can not get %d KBytes(5).", ((pVPiece.Daten->pDatenBuffer, pVPiece.Daten->lGroessepDatenBuffer, (pVPiece.Daten->lGroessepDatenBuffer + pVPiece.Daten->lGroessepDatenBuffer + lLaenge)) / 1024));
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
}
} else {
sprintf(PIECE_acString, "Can not get %s(6).", "pVPiece.Daten->InterneListe.vlnew");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlnew] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlnext
// *******************************************************************
Piece::vlnext (void *pBuffer, long *lLaenge)
{
int nRet=FALSE;
long lWert, lWert2;
void *pPointer;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->InterneListe.vlnext(&pPointer)==TRUE){
memcpy(&lWert2, pPointer, sizeof(long));
*lLaenge = lWert2;
pVPiece.Daten->lAktuellerEintrag++;
lWert = (long)(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition);
memcpy(pBuffer, &lWert, sizeof(long));
pVPiece.Daten->lPosition += lWert2;

nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlnext] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlprev
// *******************************************************************
Piece::vlprev (void *pBuffer, long *lLaenge)
{
int nRet=FALSE;
long lWert, lWert2;
void *pPointer;


if(pVPiece.nStatus==TRUE){
/*
if(pVPiece.Daten->lAktuellerEintrag>0){
memcpy(&lWert2, pPointer, sizeof(long));
} else {
lWert2 = 0;
}
*/
if(pVPiece.Daten->InterneListe.vlprev(&pPointer)==TRUE){
memcpy(&lWert2, pPointer, sizeof(long));
pVPiece.Daten->lPosition -= lWert2;
//memcpy(&lWert2, pPointer, sizeof(long));
*lLaenge = lWert2;
pVPiece.Daten->lAktuellerEintrag--;
lWert = (long)(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition);
memcpy(pBuffer, &lWert, sizeof(long));
nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlprev] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlnum
// *******************************************************************
Piece::vlnum (long lPosition, void *pBuffer, long *lLaenge)
{
int nRet=FALSE;
long lWert, lWert2, lGroesse, lMerker;
long lIndex;
void *pPointer;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->InterneListe.vlnum(lPosition, &pPointer)==TRUE){
pVPiece.Daten->InterneListe.vlreq(&pPointer, &lIndex);
lIndex--;
pVPiece.Daten->InterneListe.vlroot();
lGroesse = 0;
lWert = 0;
while(lWert<lIndex && pVPiece.Daten->InterneListe.vlnext(&pPointer)){
lWert++;
memcpy(&lMerker, pPointer, sizeof(long));
lGroesse += lMerker;
}
lIndex++;
pVPiece.Daten->InterneListe.vlnext(&pPointer);
memcpy(&lWert2, pPointer, sizeof(long));
pVPiece.Daten->lPosition = lGroesse;
*lLaenge = lWert2;
pVPiece.Daten->lAktuellerEintrag = lPosition - 1;
lWert = (long)(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition);
memcpy(pBuffer, &lWert, sizeof(long));
pVPiece.Daten->lPosition += lWert2;
pVPiece.Daten->InterneListe.vlnum(lPosition, &pPointer);
nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlnum] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlreq
// *******************************************************************
Piece::vlreq (void *pBuffer, long *lPosition, long *lLaenge)
{
int nRet=FALSE;
long lWert;
long lIndex;
void *pPointer;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->InterneListe.vlreq(&pPointer, &lIndex)==TRUE){
memcpy(&lWert, pPointer, sizeof(long));
*lLaenge = lWert;
lWert = (long)(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition);
memcpy(pBuffer, &lWert, sizeof(long));
nRet = TRUE;
*(lPosition) = lIndex;
} else {
*(lLaenge) = 0;
*(lPosition) = 0;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlreq] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlroot
// *******************************************************************
Piece::vlroot (void)
{
int nRet=FALSE;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->InterneListe.vlroot()==TRUE){
pVPiece.Daten->lPosition = 0;
pVPiece.Daten->lAktuellerEintrag = -1;
nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlroot] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vldelet
// *******************************************************************
Piece::vldelet (void *pBuffer, long *lLaenge)
{
int nRet=FALSE;
long lWert, lWert2;
long lIndex, lGroesse, lMerker;
void *pPointer;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->InterneListe.vlreq(&pPointer, &lIndex)==TRUE){
memcpy(&lWert, pPointer, sizeof(long));
pVPiece.Daten->lPosition -= lWert;
//pVPiece.Daten->lGesamtLaenge -= lWert;
lIndex--;
lGroesse = 0;
lWert2 = 0;
while(lWert2<lIndex && pVPiece.Daten->InterneListe.vlnext(&pPointer)){
lWert2++;
memcpy(&lMerker, pPointer, sizeof(long));
lGroesse += lMerker;
}
lIndex++;
memcpy(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition, pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition + lWert, lGroesse);
pVPiece.Daten->lAnzahlEintraege--;
pVPiece.Daten->InterneListe.vlnum(lIndex, &pPointer);
pVPiece.Daten->InterneListe.vldelet(&pPointer);
vlread (pBuffer, lLaenge);
nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vldelet] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vllast
// *******************************************************************
Piece::vllast (void *pBuffer, long *lLaenge)
{
int nRet=FALSE;
long lWert;
void *pPointer;
long lMerker;
long lAnzahl;


if(pVPiece.nStatus==TRUE){
pVPiece.Daten->InterneListe.vlroot();
pVPiece.Daten->InterneListe.vlanz(&lAnzahl);
if(lAnzahl>0){
pVPiece.Daten->lPosition = 0;
while(pVPiece.Daten->InterneListe.vlnext(&pPointer)){
memcpy(&lMerker, pPointer, sizeof(long));
pVPiece.Daten->lPosition += lMerker;
}
*lLaenge = lMerker;
lWert = (long)(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition - lMerker );
memcpy(pBuffer, &lWert, sizeof(long));
pVPiece.Daten->lAktuellerEintrag = pVPiece.Daten->lAnzahlEintraege - 1;
nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vllast] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlDeInit
// *******************************************************************
Piece::vlDeInit (void)
{
int nRet=FALSE;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->pDatenBuffer!=NULL){
Mem_Free(pVPiece.Daten->pDatenBuffer, pVPiece.Daten->lGroessepDatenBuffer);
}
if(pVPiece.Daten->InterneListe.vlDeInit()==TRUE){
pVPiece.nStatus = FALSE;
nRet = TRUE;
}
if(pVPiece.Daten!=NULL){
Mem_Free(pVPiece.Daten, sizeof(VPieceDaten_));
}
nRet = TRUE;
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlDeInit] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlanz
// *******************************************************************
Piece::vlanz (long *lAnzahl)
{
int nRet=FALSE;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->InterneListe.vlanz(lAnzahl)==TRUE){
nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlanz] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlswap
// *******************************************************************
Piece::vlswap (long lZielPosition, long lQuellPosition)
{
int nRet=FALSE;


if(pVPiece.nStatus==TRUE){
/*
lZielPosition++;
lQuellPosition++;
if((lZielPosition>0 && lZielPosition<pVPiece.Daten->lAnzahlEintraege + 1) && (lQuellPosition>0 && lQuellPosition<pVPiece.Daten->lAnzahlEintraege + 1)){
pBuffer = (char *)Mem_Alloc(pVPiece.Daten->lGroesseEintrag);
if(pBuffer!=NULL){
memcpy(&lWert1, (pVPiece.Daten->pIndexBuffer + lZielPosition * sizeof(long)), sizeof(long));
memcpy(pBuffer, (pVPiece.Daten->pDatenBuffer + lWert1 * pVPiece.Daten->lGroesseEintrag), pVPiece.Daten->lGroesseEintrag);

memcpy(&lWert1, (pVPiece.Daten->pIndexBuffer + lZielPosition * sizeof(long)), sizeof(long));
memcpy(&lWert2, (pVPiece.Daten->pIndexBuffer + lQuellPosition * sizeof(long)), sizeof(long));
memcpy((pVPiece.Daten->pDatenBuffer + lWert1 * pVPiece.Daten->lGroesseEintrag),(pVPiece.Daten->pDatenBuffer + lWert2 * pVPiece.Daten->lGroesseEintrag), pVPiece.Daten->lGroesseEintrag);


memcpy(&lWert1, (pVPiece.Daten->pIndexBuffer + lQuellPosition * sizeof(long)), sizeof(long));
memcpy((pVPiece.Daten->pDatenBuffer + lWert1 * pVPiece.Daten->lGroesseEintrag), pBuffer, pVPiece.Daten->lGroesseEintrag);

nRet = TRUE;
Mem_Free(pBuffer, pVPiece.Daten->lGroesseEintrag);
}
}
*/
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlswap] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlread
// *******************************************************************
Piece::vlread (void *pBuffer, long *lLaenge)
{
int nRet=FALSE;
long lWert, lIndex;
void *pPointer;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->lAktuellerEintrag>=0 && pVPiece.Daten->lAktuellerEintrag<pVPiece.Daten->lAnzahlEintraege){
pVPiece.Daten->InterneListe.vlreq(&pPointer, &lIndex);
memcpy(&lWert, pPointer, sizeof(long));
*lLaenge = lWert;
lWert = (long)(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition);
memcpy(pBuffer, &lWert, sizeof(long));
nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlread] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}

// *******************************************************************
// vlmemset
// *******************************************************************
Piece::vlmemset (void *pBuffer, long *lLaenge)
{
int nRet=FALSE;
long lWert, lIndex;
void *pPointer;


if(pVPiece.nStatus==TRUE){
if(pVPiece.Daten->lAktuellerEintrag>=0 && pVPiece.Daten->lAktuellerEintrag<pVPiece.Daten->lAnzahlEintraege){
pVPiece.Daten->InterneListe.vlreq(&pPointer, &lIndex);
memcpy(&lWert, pPointer, sizeof(long));
*lLaenge = lWert;
lWert = (long)(pVPiece.Daten->pDatenBuffer + pVPiece.Daten->lPosition);
memcpy(pBuffer, &lWert, sizeof(long));
memset((long *)lWert, 0, *lLaenge);
nRet = TRUE;
}
} else {
sprintf(PIECE_acString, "%s", "[Piece.vlmemset] pVPiece.nStatus==FALSE");
AusnahmeFehler(PIECE_acString, __CFILE__, __LINE__);
}
return(nRet);
}