Category : C Source Code
Archive   : GCOOPE10.ZIP
Filename : COLLECT.C

 
Output of file : COLLECT.C contained in archive : GCOOPE10.ZIP
/*

Collection class definition for GCOOPE 1.0

by Brian Lee Price

Released as Public Domain July, 1994.

Compatible with experimental strong typing option.

While not the best example of object oriented programming,
this class does demonstrate one method of encapsulating a
pre-defined set of functions and structures into an object
class definition.

This class maintains a contiguous section of memory divided into
fixed size slots, it makes no presumptions about the data entered
into the slots. When a slot is removed via the rmvUnit generic,
it will be cleared to all zeros. A firstFree index is maintained
which is used to find the index value to return when a call is
made via the addUnit generic. The list may be compacted by the
compact generic, this call requires a boolean parm 'sorted'. When
this parm is true the routine will 'squeeze' the list and remove
the empty slots, otherwise the routine will just reallocate if
enough empty slots exist at the end of the list to justify it.

The real value of this class is its suitability for ordered or
unordered dynamic list maintenance and its reduction of memory
fragmentation by always resizing to a multiple of MIN_LIST_ADD
slots. An inheritor of this class can manage lists which change
in size from a minimum of MIN_LIST_ADD elements to a maximum of
just under 64K in total size. The three kernel functions used by
this class form the core of the kernel's odbms.

*/

#define CLASS Collection

#define _INTERNAL_

#include "gcoope10.h"

#include

object CLASS;

extern object Unsigned;

/*

This class uses a portion of the internal PCOOPE kernel to save code:

-#define DYNLIST_STRU word elemSize,firstFree,maxElems;void * listPtr

-#define MAX_BLOCK_SIZE (65523L)

-#define MIN_LIST_ADD 16

the following functions are defined in listmgr.c

int addItem(void *listPtr, int elemSize);
int rmvItem(void *listPtr, int elemNdx);
stat compactList(void *listAdr, boolean sorted);

*/

typedef struct {
DYNLIST_STRU;
} instVars;

USEGEN(addUnit);
USEGEN(rmvUnit);
USEGEN(getUnit);
USEGEN(valueOf);
USEGEN(sizeOf);
USEGEN(addressOf);
USEGEN(reSize);
USEGEN(changeVal);
USEGEN(compact);
USEGEN(numElems);


cmethod object m4New(object instance, word elemSize)
{
instVars * ivptr;

if(NULL==(ivptr=makeInst(&instance))) return 0;
ivptr->elemSize=elemSize;
ivptr->listPtr=NULL;
g(New)(ST(Unsigned),0);
return instance;
}


/* returns the offset of the newly created slot */

imethod int m4addUnit(object instance, void * newUnit)
{
instVars * ivptr;
char * newSlot;
int offset=-1;

if(NULL==(ivptr=getIVptr(instance))) goto end;
if((offset=addItem(ivptr->listPtr, ivptr->elemSize))<0) goto end;
if(newUnit)
{
newSlot=ivptr->listPtr;
newSlot+= ivptr->elemSize * offset;
memcpy(newSlot, newUnit, ivptr->elemSize);
}
g(GEN(changeVal))(ST(Unsigned),
(unsigned short) ((UNSGNDRV)g)(GEN(valueOf))(instance)+1);

end:
return offset;
}


imethod object m4rmvUnit(object instance, int index)
{
instVars * ivptr;

if((NULL==(ivptr=getIVptr(instance))) ||
(rmvItem(ivptr->listPtr, index)<0)) return FUNCFAIL;
g(GEN(changeVal))(ST(Unsigned),
(unsigned short) ((UNSGNDRV)g)(GEN(valueOf))(instance)+1);

return FUNCOKAY;
}


imethod void * m4getUnit(object instance, int index)
{
instVars * ivptr;

if((NULL==(ivptr=getIVptr(instance))) ||
(index<0) || (index>ivptr->maxElems)) return NULL;
else return (((char *) (ivptr->listPtr))+ index * ivptr->elemSize);
}


imethod word m4sizeOf(object instance)
{
return ((instVars *) getIVptr(instance))->elemSize;
}


imethod void * m4addressOf(object instance)
{
return ((instVars *) getIVptr(instance))->listPtr;
}


imethod object m4reSize(object instance, unsigned short newNumElems)
{
instVars * ivptr;
int newSize;
void * temp;

if(NULL==(ivptr=getIVptr(instance))
|| NULL==ivptr->listPtr) return FUNCFAIL;
newSize=newNumElems;
newNumElems/=MIN_LIST_ADD;
if(newSize % MIN_LIST_ADD) newNumElems++;
newNumElems*=MIN_LIST_ADD;
newSize = ivptr->elemSize * newNumElems;
if(newSize < ivptr->maxElems)
{
ivptr->listPtr=s_realloc(ivptr->listPtr, newSize);
if(ivptr->firstFree>newNumElems) ivptr->firstFree=newNumElems;
if(g(GEN(valueOf))(Unsigned) > newNumElems)
g(GEN(changeVal))(ST(Unsigned), newNumElems);
}
else
{
temp = s_calloc(1, newSize);
memcpy(temp, ivptr->listPtr, ivptr->maxElems);
s_free(ivptr->listPtr);
ivptr->listPtr=temp;
}
ivptr->maxElems=newNumElems;
return FUNCOKAY;
}


imethod object m4compact(object instance, boolean sorted)
{
instVars * ivptr;

if(NULL==(ivptr=getIVptr(instance))
|| NULL==ivptr->listPtr) return FUNCFAIL;
return compactList(ivptr->listPtr, sorted);
}


cmethod object m4Kill(object instance)
{
s_free(((instVars *) getIVptr(instance))->listPtr);
g(Kill)(Object, instance);
return instance;
}


CLASS_INSTALL
{
if(END==(CLASS=g(New)(Class, 0, sizeof(instVars), Unsigned, END))) goto err;
if(addGMthd(CLASS, New, (method) m4New)) goto err;
if(addGMthd(CLASS, Kill, (method) m4Kill)) goto err;
if(addGMthd(CLASS, GEN(addUnit), (method) m4addUnit)) goto err;
if(addGMthd(CLASS, GEN(rmvUnit), (method) m4rmvUnit)) goto err;
if(addGMthd(CLASS, GEN(getUnit), (method) m4getUnit)) goto err;
if(rmvGMthd(CLASS, GEN(changeVal))) goto err;
if(addGMthd(CLASS, GEN(sizeOf), (method) m4sizeOf)) goto err;
if(addGMthd(CLASS, GEN(addressOf), (method) m4addressOf)) goto err;
if(addGMthd(CLASS, GEN(reSize), (method) m4reSize)) goto err;
if(addGMthd(CLASS, GEN(compact), (method) m4compact)) goto err;
if(RENGM(valueOf, Unsigned, numElems)) goto err;
return FUNCOKAY;

err:
return FUNCFAIL;
}



  3 Responses to “Category : C Source Code
Archive   : GCOOPE10.ZIP
Filename : COLLECT.C

  1. Very nice! Thank you for this wonderful archive. I wonder why I found it only now. Long live the BBS file archives!

  2. This is so awesome! 😀 I’d be cool if you could download an entire archive of this at once, though.

  3. But one thing that puzzles me is the “mtswslnkmcjklsdlsbdmMICROSOFT” string. There is an article about it here. It is definitely worth a read: http://www.os2museum.com/wp/mtswslnk/