Exemplo n.º 1
0
/*------------------------------------------------------------------------
 Procedure:     Add ID:1
 Purpose:       Adds a string to the string collection.
 Input:         The collection and the string to be added to it
 Output:        Number of items in the collection or <= 0 if error
 Errors:
------------------------------------------------------------------------*/
static int Add(ElementType *SC,const CHAR_TYPE *newval)
{
    if (SC == NULL) {
        return NullPtrError("Add");
    }

    if (SC->Flags & CONTAINER_READONLY)
        return ReadOnlyError(SC,"Add");
    if ((SC->count+1) >= SC->capacity) {
        int r = Resize(SC);
        if (r <= 0)
            return r;
    }

    if (newval) {
        SC->contents[SC->count] = DuplicateString(SC,newval,"Add");
        if (SC->contents[SC->count] == NULL) {
            return 0;
        }
    }
    else
        SC->contents[SC->count] = NULL;
    SC->timestamp++;
    ++SC->count;
    return 1;
}
Exemplo n.º 2
0
static int SetCapacity(ElementType *SC,size_t newCapacity)
{
    CHAR_TYPE **newContents;
    if (SC == NULL) {
        return NullPtrError("SetCapacity");
    }
    if (SC->Flags & CONTAINER_READONLY) {
        return ReadOnlyError(SC,"SetCapacity");
    }
    newContents = SC->Allocator->malloc(newCapacity*sizeof(void *));
    if (newContents == NULL) {
        return NoMemoryError(SC,"SetCapacity");
    }
    memset(SC->contents,0,sizeof(void *)*newCapacity);
    SC->capacity = newCapacity;
    if (newCapacity > SC->count)
        newCapacity = SC->count;
    else if (newCapacity < SC->count)
        SC->count = newCapacity;
    if (newCapacity > 0) {
        memcpy(newContents,SC->contents,newCapacity*sizeof(void *));
    }
    SC->Allocator->free(SC->contents);
    SC->contents = newContents;
    SC->timestamp++;
    return 1;
}
Exemplo n.º 3
0
static int EraseInternal(ElementType *SC,const CHAR_TYPE *str,int all)
{
    size_t i;
    int result = CONTAINER_ERROR_NOTFOUND;
    if (SC == NULL) {
        return NullPtrError("Erase");
    }
    if (str == NULL) {
        return BadArgError(SC,"Erase");
    }
    if (SC->Flags & CONTAINER_READONLY)
        return ReadOnlyError(SC,"Erase");
    for (i=0; i<SC->count;i++) {
        if (!SC->strcompare((const void **)&SC->contents[i],
                            (const void **)&str,SC->StringCompareContext)) {
            if (SC->DestructorFn) SC->DestructorFn(SC->contents[i]);
            SC->Allocator->free(SC->contents[i]);
            if (i < (SC->count-1))
                memmove(SC->contents+i,SC->contents+i+1,(SC->count-i)*sizeof(char *));
            --SC->count;
            SC->contents[SC->count]=NULL;
            SC->timestamp++;
            result = 1;
            if (all == 0) break;
            i--;
        }
    }
    return result;
}
Exemplo n.º 4
0
static int Reverse(ElementType *SC)
{
    CHAR_TYPE **p, **q, *t;

    if (SC == NULL) {
        return NullPtrError("Reverse");
    }
    if (SC->Flags & CONTAINER_READONLY) {
        return ReadOnlyError(SC,"Reverse");
    }
    if (SC->count < 2)
        return 1;

    p = SC->contents;
    q = &p[SC->count-1];
    while ( p < q ) {
        t = *p;
        *p = *q;
        *q = t;
        p++;
        q--;
    }
    SC->timestamp++;
    return 1;
}
Exemplo n.º 5
0
static int Append(ElementType *SC1, ElementType *SC2)
{
    if (SC1 == NULL || SC2 == NULL) {
        return NullPtrError("Append");
    }
    if (SC1->Flags & CONTAINER_READONLY) {
        return ReadOnlyError(SC1,"Append");
    }
    return AddRange(SC1,SC2->count,(const CHAR_TYPE **)SC2->contents);
}
Exemplo n.º 6
0
static int InsertIn(ElementType *source, size_t idx, ElementType *newData)
{
    size_t newCount,i,j,siz;
    CHAR_TYPE **p,**oldcontents;

    if (source == NULL || newData == NULL) {
        return NullPtrError("InsertIn");
    }
    if (source->Flags & CONTAINER_READONLY)
        return ReadOnlyError(source,"InsertIn");
    if (idx > source->count) {
        return IndexError(source,idx,"InsertIn");
    }
    newCount = source->count + newData->count;
    if (newData->count == 0)
        return 1;
    if (newCount == 0)
        return 1;
    if (newCount >= (source->capacity-1)) {
        int r = ResizeTo(source,1+newCount+newCount/4);
        if (r <= 0)
            return r;
    }
    p = source->contents;
    siz = source->capacity*sizeof(CHAR_TYPE *);
    oldcontents = source->Allocator->malloc(siz);
    if (oldcontents == NULL) {
        return NoMemoryError(source,"InsertIn");
    }
    memset(oldcontents,0,siz);
    memcpy(oldcontents,p,sizeof(char *)*source->count);
    if (idx < source->count) {
        memmove(p+(idx+newData->count),
                p+idx,
                (source->count-idx)*sizeof(char *));
    }
    for (i=idx,j=0; i<idx+newData->count;i++,j++) {
        source->contents[i] = DuplicateString(newData,newData->contents[j],"InsertIn");
        if (source->contents[i] == NULL) {
            source->Allocator->free(source->contents);
            source->contents = oldcontents;
            return NoMemoryError(source,"InsertIn");
        }
    }
    source->Allocator->free(oldcontents);
    source->timestamp++;
    source->count = newCount;
    return 1;
}
Exemplo n.º 7
0
void Variable::verifyWritable(Value const &attemptedNewValue)
{
    if(d->mode & ReadOnly)
    {
        if(d->value && typeid(*d->value) == typeid(attemptedNewValue) &&
           !d->value->compare(attemptedNewValue))
        {
            // This is ok: the value doesn't change.
            return;
        }

        /// @throw ReadOnlyError  The variable is in read-only mode.
        throw ReadOnlyError("Variable::verifyWritable", 
            "Variable '" + d->name + "' is in read-only mode");
    }
}
Exemplo n.º 8
0
static CHAR_TYPE *GetElement(const ElementType *SC,size_t idx)
{
    if (SC == NULL) {
        NullPtrError("GetElement");
        return NULL;
    }
    if (SC->Flags & CONTAINER_READONLY) {
        ReadOnlyError(SC,"GetElement");
        return NULL;
    }
    if (idx >=SC->count) {
        IndexError(SC,idx,"GetElement");
        return NULL;
    }
    return SC->contents[idx];
}
Exemplo n.º 9
0
static int Sort(ElementType *SC)
{
    CompareInfo ci;

    ci.ExtraArgs = NULL;
    ci.ContainerLeft = SC;
    ci.ContainerRight = NULL;
    if (SC == NULL) {
        return NullPtrError("Sort");
    }
    if (SC->Flags & CONTAINER_READONLY) {
        return ReadOnlyError(SC,"Sort");
    }
    qsortEx(SC->contents,SC->count,sizeof(char *),(CompareFunction)SC->strcompare,&ci);
    SC->timestamp++;
    return 1;
}
Exemplo n.º 10
0
static int Clear(ElementType *SC)
{
    size_t i;

    if (SC == NULL) {
        return NullPtrError("Clear");
    }
    if (SC->Flags & CONTAINER_READONLY)
        return ReadOnlyError(SC,"Clear");
    for (i=0; i<SC->count;i++) {
        if (SC->DestructorFn)
            SC->DestructorFn(SC->contents[i]);
        SC->Allocator->free(SC->contents[i]);
        SC->contents[i] = NULL;
    }
    SC->count = 0;
    SC->timestamp=0;
    SC->Flags=0;
    return 1;
}
Exemplo n.º 11
0
static int InsertAt(ElementType *SC,size_t idx,const CHAR_TYPE *newval)
{
    CHAR_TYPE *p;
    if (SC == NULL) {
        return NullPtrError("InsertAt");
    }
    if (newval == NULL) {
        return BadArgError(SC,"InsertAt");
    }
    if (SC->Flags & CONTAINER_READONLY) {
        return ReadOnlyError(SC,"InsertAt");
    }
    if (idx >= SC->count) {
        return IndexError(SC,idx,"InsertAt");
    }
    if ((SC->count+1) >= SC->capacity) {
        int r = Resize(SC);
        if (r <= 0)
            return r;
    }
    p = DuplicateString(SC,newval,"InsertAt");
    if (p == NULL) {
        return NoMemoryError(SC,"InsertAt");
    }

    if (idx == 0) {
        if (SC->count > 0)
            memmove(SC->contents+1,SC->contents,SC->count*sizeof(CHAR_TYPE *));
        SC->contents[0] = p;
    }
    else if (idx == SC->count) {
        SC->contents[idx] = p;
    }
    else if (idx < SC->count) {
        memmove(SC->contents+idx+1,SC->contents+idx,(SC->count-idx+1)*sizeof(CHAR_TYPE *));
        SC->contents[idx] = p;
    }
    SC->timestamp++;
    ++SC->count;
    return 1;
}
Exemplo n.º 12
0
static int PushBack(ElementType *SC,const CHAR_TYPE *str)
{
    CHAR_TYPE *r;

    if (SC == NULL)
        return NullPtrError("PushBack");
    if (SC->Flags&CONTAINER_READONLY) {
        return ReadOnlyError(SC,"PushBack");
    }
    if (SC->count >= SC->capacity-1) {
        int res = Resize(SC);
        if (res <= 0)
            return res;
    }
    r = DuplicateString(SC,str,"Push");
    if (r == NULL)
        return 0;
    SC->contents[SC->count++] = r;
    SC->timestamp++;
    return 1;
}
Exemplo n.º 13
0
/* [email protected] (gerome) proposed calling DuplicateString. Good
suggestion */
static int ReplaceAt(ElementType *SC,size_t idx,CHAR_TYPE *newval)
{
    CHAR_TYPE *r;

    if (SC == NULL) {
        return NullPtrError("ReplaceAt");
    }
    if (SC->Flags & CONTAINER_READONLY) {
        return ReadOnlyError(SC,"ReplaceAt");
    }
    if (idx >= SC->count) {
        return IndexError(SC,idx,"ReplaceAt");
    }
    SC->Allocator->free(SC->contents[idx]);
    r = DuplicateString(SC,newval,(char *)"ReplaceAt");
    if (r == NULL) {
        return NoMemoryError(SC,"ReplaceAt");
    }
    SC->contents[idx] = r;
    SC->timestamp++;
    return 1;
}
Exemplo n.º 14
0
static int Finalize(ElementType *SC)
{
    size_t i;

    if (SC == NULL) {
        return CONTAINER_ERROR_BADARG;
    }
    if (SC->Flags & CONTAINER_READONLY) {
        return ReadOnlyError(SC,"Finalize");
    }

    for (i=0; i<SC->count;i++) {
        if (SC->DestructorFn)
            SC->DestructorFn(SC->contents[i]);
        SC->Allocator->free(SC->contents[i]);
    }
    SC->Allocator->free(SC->contents);
    if (SC->VTable != &INTERFACE_OBJECT)
        SC->Allocator->free(SC->VTable);
    SC->Allocator->free(SC);
    return 1;
}
Exemplo n.º 15
0
static int RemoveAt(ElementType *SC,size_t idx)
{
    if (SC == NULL) {
        return NullPtrError("RemoveAt");
    }
    if (idx >= SC->count )
        return IndexError(SC,idx,"RemoveAt");
    if (SC->Flags & CONTAINER_READONLY)
        return ReadOnlyError(SC,"RemoveAt");
    /* Test for remove of an empty collection */
    if (SC->count == 0)
        return 0;
    if (SC->DestructorFn)
        SC->DestructorFn(SC->contents[idx]);
    SC->Allocator->free(SC->contents[idx]);
    if (idx < (SC->count-1)) {
        memmove(SC->contents+idx,SC->contents+idx+1,(SC->count-idx)*sizeof(char *));
    }
    SC->contents[SC->count-1]=NULL;
    SC->timestamp++;
    --SC->count;
    return 1;
}
Exemplo n.º 16
0
static int AddRange(ElementType *SC,size_t n, const CHAR_TYPE **data)
{
    size_t newcapacity;
    CHAR_TYPE **p;

    if (n == 0)
        return 1;
    if (SC == NULL) {
        return NullPtrError("AddRange");
    }
    if (data == NULL) {
        return BadArgError(SC,"AddRange");
    }
    if (SC->Flags & CONTAINER_READONLY) {
        return ReadOnlyError(SC,"AddRange");
    }

    newcapacity = SC->count+n;
    if (newcapacity >= SC->capacity-1) {
        CHAR_TYPE **newcontents;
        newcapacity += SC->count/4;
        newcontents = SC->Allocator->realloc(SC->contents,newcapacity*sizeof(void *));
        if (newcontents == NULL) {
            return NoMemoryError(SC,"AddRange");
        }
        SC->capacity = newcapacity;
        SC->contents = newcontents;
    }
    p = SC->contents;
    p += SC->count;
    memcpy(p,data,n*sizeof(void *));
    SC->count += n;
    SC->timestamp++;

    return 1;
}