//
// Stack BN 24-Mai-98
//
//
//
//
#include <stdlib.h>
#include <malloc.h>
#include <string.h>

#include "WinMain.h"
#include "System.h"
#include "Stack.h"

#define DATENBLOCKANZAHL 1024

// *******************************************************************
// vlInit
// *******************************************************************
Stack::vlInit (void)
{
VStack_ *pStruktur;


pStruktur = &pVStack;
pStruktur->nStatus = FALSE;
pStruktur->Daten = (VStackDaten_ *)Mem_Alloc(sizeof(VStackDaten_));
if(pStruktur->Daten!=NULL){
memset(pStruktur->Daten, 0, sizeof(VStackDaten_));
if(pStruktur->Daten->InterneListe.vlInit()==TRUE){
pStruktur->Daten->nErsterDurchlauf = TRUE;
pStruktur->nStatus = TRUE;
return(TRUE);
} else {
return(FALSE);
}
} else {
return(FALSE);
}
return(pStruktur->nStatus);
}

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


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

//lWert = (long)(pVStack.Daten->pDatenBuffer + pVStack.Daten->lAktuellerEintrag * lLaenge);
memcpy((pVStack.Daten->pDatenBuffer + pVStack.Daten->lAktuellerEintrag * lLaenge), pBuffer, lLaenge);
pVStack.Daten->lPosition += lLaenge;
nRet = TRUE;
} else {
vlDeInit();
}
} else {
if(pVStack.Daten->InterneListe.vlnew(&pPointer, sizeof(long))==TRUE){
memcpy(pPointer, &lLaenge, sizeof(long));
pVStack.Daten->InterneListe.vlreq(&pPointer, &lIndex);
lIndex--;
pVStack.Daten->InterneListe.vlroot();
lGroesse = 0;
lWert = 0;
while(pVStack.Daten->InterneListe.vlnext(&pPointer) && lWert<lIndex){
lWert++;
memcpy(&lMerker, pPointer, sizeof(long));
lGroesse += lMerker;
}
lIndex++;
pVStack.Daten->InterneListe.vlnext(&pPointer);

if((lGroesse + lLaenge)<pVStack.Daten->lGroessepDatenBuffer){
memcpy(pVStack.Daten->pDatenBuffer + lGroesse + lLaenge, pVStack.Daten->pDatenBuffer + lGroesse, lLaenge);
//lWert = (long)(pVStack.Daten->pDatenBuffer + lGroesse);
memcpy((pVStack.Daten->pDatenBuffer + lGroesse), pBuffer, lLaenge);
pVStack.Daten->lAnzahlEintraege++;
pVStack.Daten->lPosition += lLaenge;
nRet = TRUE;
} else {
pVStack.Daten->pDatenBuffer = (char *)Mem_ReAlloc(pVStack.Daten->pDatenBuffer, pVStack.Daten->lGroessepDatenBuffer, (pVStack.Daten->lGroessepDatenBuffer + pVStack.Daten->lGroessepDatenBuffer + lLaenge));
if(pVStack.Daten->pDatenBuffer!=NULL){
memset(pVStack.Daten->pDatenBuffer + pVStack.Daten->lGroessepDatenBuffer, 0, pVStack.Daten->lGroessepDatenBuffer + lLaenge);
pVStack.Daten->lGroessepDatenBuffer = (pVStack.Daten->lGroessepDatenBuffer + pVStack.Daten->lGroessepDatenBuffer + lLaenge);
//lWert = (long)(pVStack.Daten->pDatenBuffer + lGroesse);
memcpy((pVStack.Daten->pDatenBuffer + lGroesse), pBuffer, lLaenge);
pVStack.Daten->lAnzahlEintraege++;
pVStack.Daten->lPosition += lLaenge;
nRet = TRUE;
}

}
}
}
}
return(nRet);
}

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


if(pVStack.nStatus==TRUE){
if(pVStack.Daten->InterneListe.vlreq(&pPointer, &lIndex)==TRUE){
memcpy(&lWert, pPointer, sizeof(long));
pVStack.Daten->lPosition -= lWert;
lIndex--;
lGroesse = 0;
lWert2 = 0;
while(lWert2<lIndex && pVStack.Daten->InterneListe.vlnext(&pPointer)){
lWert2++;
memcpy(&lMerker, pPointer, sizeof(long));
lGroesse += lMerker;
}
lIndex++;

memcpy(pBuffer, pVStack.Daten->pDatenBuffer + pVStack.Daten->lPosition, lWert);
*lLaenge = lWert;
//lWert = (long)(pVStack.Daten->pDatenBuffer + pVStack.Daten->lPosition);
//memcpy(pBuffer, &lWert, sizeof(long));

memcpy(pVStack.Daten->pDatenBuffer + pVStack.Daten->lPosition, pVStack.Daten->pDatenBuffer + pVStack.Daten->lPosition + lWert, lGroesse);
pVStack.Daten->lAnzahlEintraege--;
pVStack.Daten->InterneListe.vlnum(lIndex, &pPointer);
pVStack.Daten->InterneListe.vldelet(&pPointer);

nRet = TRUE;
}
}
return(nRet);
}

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


if(pVStack.nStatus==TRUE){
if(pVStack.Daten->pDatenBuffer!=NULL){
Mem_Free(pVStack.Daten->pDatenBuffer, pVStack.Daten->lGroessepDatenBuffer);
}
if(pVStack.Daten->InterneListe.vlDeInit()==TRUE){
pVStack.nStatus = FALSE;
nRet = TRUE;
}
if(pVStack.Daten!=NULL){
Mem_Free(pVStack.Daten, sizeof(VStackDaten_));
}
nRet = TRUE;
}
return(nRet);
}

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


if(pVStack.nStatus==TRUE){
if(pVStack.Daten->InterneListe.vlanz(lAnzahl)==TRUE){
nRet = TRUE;
}
}
return(nRet);
}