107 lines
3.3 KiB
C
Executable File
107 lines
3.3 KiB
C
Executable File
/* s4next.c (c)Copyright Sequiter Software Inc., 1988-1996. All rights reserved. */
|
|
|
|
#include "d4all.h"
|
|
#ifndef S4UNIX
|
|
#ifdef __TURBOC__
|
|
#pragma hdrstop
|
|
#endif
|
|
#endif
|
|
|
|
int s4nextSpoolEntry( SORT4 *s4 )
|
|
{
|
|
long lastDiskPos, diskDataLeft, newRec, spoolRec ;
|
|
unsigned maxRead, lenRead ;
|
|
int low, high, pos, rc ;
|
|
char *newData ;
|
|
S4SPOOL saveSpool ;
|
|
|
|
#ifdef E4PARM_LOW
|
|
if ( s4 == 0 )
|
|
return error4( 0, e4parm_null, E91908 ) ;
|
|
#endif
|
|
|
|
s4->spoolPointer->pos += s4->totLen ;
|
|
if ( s4->spoolPointer->pos >= s4->spoolPointer->len )
|
|
{
|
|
s4->spoolPointer->pos = 0 ;
|
|
if ( s4->spoolPointer->disk >= 0L )
|
|
{
|
|
lastDiskPos = (s4->spoolPointer->spoolI+1) * s4->spoolDiskLen ;
|
|
diskDataLeft = lastDiskPos - s4->spoolPointer->disk ;
|
|
maxRead = s4->spoolMemLen ;
|
|
if ( (long) s4->spoolMemLen > diskDataLeft )
|
|
maxRead = (unsigned) diskDataLeft ;
|
|
lenRead = file4read( &s4->file, s4->spoolPointer->disk, s4->spoolPointer->ptr, maxRead) ;
|
|
|
|
if ( error4code( s4->codeBase ) < 0 )
|
|
{
|
|
sort4free( s4 ) ;
|
|
return error4stack( s4->codeBase, (short)error4code( s4->codeBase ), E91908 ) ;
|
|
}
|
|
|
|
s4->spoolPointer->len = lenRead ;
|
|
s4->spoolPointer->disk += lenRead ;
|
|
if ( lenRead != maxRead || lenRead == 0 )
|
|
{
|
|
if ( lenRead % s4->totLen )
|
|
{
|
|
sort4free( s4 ) ;
|
|
return error4describe( s4->codeBase, e4read, E91908, s4->file.name, 0, 0 ) ;
|
|
}
|
|
s4->spoolPointer->disk = -1 ;
|
|
if ( lenRead == 0 )
|
|
{
|
|
s4deleteSpoolEntry( s4 ) ;
|
|
return 0 ;
|
|
}
|
|
else
|
|
s4->spoolPointer->len = lenRead ;
|
|
}
|
|
else /* Check if we are out of disk entries for the spool */
|
|
if ( s4->spoolPointer->disk >= lastDiskPos )
|
|
s4->spoolPointer->disk = -1L ;
|
|
}
|
|
else
|
|
{
|
|
s4deleteSpoolEntry(s4) ;
|
|
return 0 ;
|
|
}
|
|
}
|
|
|
|
/* Position the new entry to the sorted location using a binary search */
|
|
/* New entry is placed before 'result': int pos >= 1 when complete */
|
|
low = 1 ;
|
|
high = s4->spoolsN ;
|
|
newData = s4->spoolPointer->ptr + s4->spoolPointer->pos ;
|
|
memcpy( (void *)&newRec, newData + s4->sortLen, sizeof(newRec) ) ;
|
|
|
|
for(;;)
|
|
{
|
|
pos = ( low + high ) / 2 ;
|
|
if ( pos == low && pos == high ) /* then found */
|
|
{
|
|
memcpy( (void *)&saveSpool, (void *)s4->spoolPointer, sizeof(S4SPOOL) ) ;
|
|
c4memmove( s4->spoolPointer, s4->spoolPointer+1, sizeof(S4SPOOL)*(pos-1) ) ;
|
|
memcpy( (void *)(s4->spoolPointer+pos-1), (void *)&saveSpool, sizeof(S4SPOOL) ) ;
|
|
return 0 ;
|
|
}
|
|
rc = (*s4->cmp)(newData, s4->spoolPointer[pos].ptr + s4->spoolPointer[pos].pos, s4->sortLen) ;
|
|
if ( rc == 0 )
|
|
{
|
|
memcpy( (void *)&spoolRec, s4->spoolPointer[pos].ptr + s4->spoolPointer[pos].pos + s4->sortLen, sizeof(spoolRec) ) ;
|
|
if ( newRec > spoolRec )
|
|
rc = 1 ;
|
|
}
|
|
|
|
if ( rc > 0 )
|
|
low = pos+1 ;
|
|
else
|
|
high = pos ;
|
|
#ifdef E4ANALYZE
|
|
if ( high < low )
|
|
return error4( s4->codeBase, e4result, E91908 ) ;
|
|
#endif
|
|
}
|
|
}
|
|
|