#include "darray.h"
/*****************************************************************************/
darray* darr_create(ssize_t data_size, ssize_t init_size)
{
//PRINT("\n");
int i = 0;
darray *arr = NULL;
if ( init_size <= 0 )
{
printf("initial darray size should be >0\n");
goto error;
}
arr = malloc(sizeof(darray));
if ( arr == NULL )
{
printf("cannot allocalte mem\n");
goto error;
}
arr->max = init_size;
arr->data = malloc(init_size*sizeof(uint8_t *));
if (arr->data == NULL)
{
printf("Cannot allocate mem for data\n");
goto error;
}
for (i=0;i<init_size;i++)
{
arr->data[i] = NULL;
}
arr->end = 0;
arr->size = data_size;
arr->expand = DEFAULT_EXPAND_RATE;
return arr;
error:
if ( arr != NULL )
{
free( arr );
arr = NULL;
}
ERROR("\n");
return NULL;
}
/*****************************************************************************/
void darr_destroy(darray *da)
{
//PRINT("\n");
if(da)
{
if(da->data)
{
free(da->data);
}
free(da);
da = NULL;
}
}
/*****************************************************************************/
void darr_clear(darray *da)
{
//PRINT("\n");
int i = 0;
if(da->size > 0)
{
for(i = 0; i < da->max; i++)
{
if(da->data[i] != NULL)
{
free(da->data[i]);
}
}
}
}
/*****************************************************************************/
void darr_clear_idx(darray *da, int idx)
{
if ( idx > da->max )
{
return;
}
if (idx > da->end )
{
return;
}
if (da->data[idx] != NULL)
{
//PRINT("free=0x%08x\n", da->data[idx]);
free( da->data[idx] );
da->data[idx] = NULL;
}
}
/*****************************************************************************/
int darr_expand(darray *da)
{
//PRINT("\n");
size_t old_max = da->max;
if ( darr_resize(da, da->max + da->expand ) != 0 )
{
printf("Couldnt resize\n");
goto error;
}
memset(da->data + old_max, 0, da->expand + 1);
return 0;
error:
ERROR("\n");
return -1;
}
/*****************************************************************************/
int darr_resize(darray *da, ssize_t size)
{
//PRINT("\n");
int i = 0;
void *data = NULL;
if (size < 1)
{
printf("new size smaller then 1\n");
goto error;
}
//PRINT("max-0x%08x=new-0x%08x\n",da->max, size);
if (size < da->max)
{
i = da->max;
do
{
if ( da->data[i-1] != NULL )
{
free(da->data[i-1]);
da->data[i-1] = NULL;
}
i -= 1;
} while ( i-1 == size );
}
da->max = size;
data = realloc(da->data, da->max * sizeof(void *));
// check contents and assume realloc doesn't harm the original on error
if ( data == NULL )
{
printf("Cannot relocate data\n");
goto error;
}
da->data = data;
return 0;
error:
ERROR("\n");
return -1;
}
/*****************************************************************************/
int darr_contract(darray *da)
{
//PRINT("\n");
int sz = -1;
if ( da->end < da->expand )
{
sz = da->expand;
} else {
sz = da->end;
}
return darr_resize(da, sz + 1);
}
/*****************************************************************************/
int darr_push(darray *da, void *val)
{
//PRINT("\n");
if (da->data[da->end] != NULL)
{
ERROR("\n");
}
da->data[da->end] = val;
da->end++;
if(darr_end(da) >= darr_max(da))
{
return darr_expand(da);
}
return 0;
}
/*****************************************************************************/
void* darr_pop(darray *da)
{
//PRINT("\n");
void *val = NULL;
if ( da->end-1 < 0 )
{
printf("Cannot pop value empty stack\n");
goto error;
}
val = darr_remove(da, da->end - 1);
da->end--;
if((darr_end(da) > (int)da->expand) &&
(darr_end(da) % da->expand))
{
darr_contract(da);
}
return val;
error:
ERROR("\n");
return NULL;
}
/*****************************************************************************/
void darr_clear_destroy(darray *da)
{
//PRINT("\n");
darr_clear(da);
darr_destroy(da);
}
/*****************************************************************************/
int darr_set(darray *da, int idx, void *val)
{
//PRINT("\n");
if ( idx >= da->max )
{
printf("setting param out of range\n");
goto error;
}
if(idx > da->end)
{
da->end = idx;
}
//PRINT("idx=%d ptr=%x\n",idx,val);
da->data[idx] = val;
return 0;
error:
ERROR("\n");
return -1;
}
/*****************************************************************************/
void* darr_get(darray *da, int idx)
{
//PRINT("\n");
if ( idx >= da->end )
{
printf("gettin value out of range\n");
goto error;
}
//PRINT("idx=%d\n",idx);
//PRINT("end=%d\n",da->end);
//PRINT("max=%d\n",da->max);
//PRINT("data=0x%x\n",da->data);
return da->data[idx];
error:
ERROR("\n");
return NULL;
}
/*****************************************************************************/
void* darr_remove(darray *da, int idx)
{
//PRINT("\n");
void *val = NULL;
val = da->data[idx];
da->data[idx] = NULL;
return val;
}
/*****************************************************************************/
void* darr_new(darray *da)
{
//PRINT("\n");
if ( da->size < 1 )
{
printf("data element size <1\n");
goto error;
}
return calloc(1, da->size);
error:
ERROR("\n");
return NULL;
}
/*****************************************************************************/
int darr_isidx(darray *da, int idx)
{
if ( idx < 0)
return 0;
if ( idx < da->end )
return 1;
return 0;
}