common/vector.c

00001 /*
00002  * Copyright Ian Burnett 2005, 2006.
00003  *
00004  * This file is part of Ian's Interactive LCD controller (IILC).
00005  * 
00006  * IILC is free software; you can redistribute it and/or modify it under
00007  * the terms of the GNU General Public License as published by the Free
00008  * Software Foundation; either version 2 of the License, or (at your
00009  * option) any later version.
00010  *
00011  * IILC is distributed in the hope that it will be useful, but WITHOUT
00012  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
00013  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
00014  * for more details.
00015  *
00016  * You should have received a copy of the GNU General Public License along
00017  * with IILC; if not, write to the Free Software Foundation, Inc.,
00018  * 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA.
00019  */
00020 
00021 
00022 #include <string.h>
00023 
00024 #include "vector.h"
00025 #include "trace.h"
00026 
00027 
00028 #define IILC_MODULE MODULE_TYPE_APP
00029 
00030 #define INITIAL_VECTOR_CAPACITY 20
00031 
00032 typedef struct _tag_vector
00033 {
00034     void ** pData;
00035 
00036     int nCapacity;
00037 
00038     int nSize;
00039     
00040     int nHiElement;
00041 
00042 } VECTOR;
00043 
00044 
00045 int vectorCreate(LPVECTOR * ppVector)
00046 {
00047     int rc = 0;
00048     LPVECTOR pVector = NULL;
00049 
00050     IILC_TRACE_ENTRY(IILC_MODULE, T_vectorCreate);
00051     traceDebug(IILC_TRACE_CONTEXT, "ppVector %p", ppVector);
00052 
00053     /* Allocate the memory */
00054     pVector = (LPVECTOR) malloc(sizeof(VECTOR));
00055     if (pVector == NULL) {
00056         rc = ERR_MEM_ALLOC_FAILED;
00057         traceError(IILC_TRACE_CONTEXT, "Vector memory allocation failed");
00058         goto end_of_function;
00059     }
00060 
00061     /* Init the structure */
00062     pVector->pData      = NULL;
00063     pVector->nCapacity  = INITIAL_VECTOR_CAPACITY;
00064     pVector->nSize      = 0;
00065     pVector->nHiElement = INITIAL_VECTOR_CAPACITY;
00066 
00067     /* Allocate an initial array */
00068     pVector->pData = (void **) calloc(pVector->nCapacity, sizeof(void *));
00069     if (pVector->pData == NULL) {
00070         rc = ERR_MEM_ALLOC_FAILED;
00071         traceError(IILC_TRACE_CONTEXT, "Failed to allocate vector array");
00072         goto end_of_function;
00073     }
00074 
00075     /* Assign to the user */
00076     *ppVector = pVector;
00077 
00078 end_of_function:
00079 
00080     /* Cleanup as necessary */
00081     if (rc) {
00082         if (pVector) {
00083             if (pVector->pData) { free(pVector->pData); }
00084             free(pVector);
00085         }
00086     }
00087 
00088     IILC_TRACE_EXIT_RC(rc);
00089     return rc;
00090 }
00091 
00092 int vectorDestroy(LPVECTOR * ppVector)
00093 {
00094     LPVECTOR pVector = *ppVector;
00095 
00096     free(pVector->pData);
00097 
00098     free(pVector);
00099 
00100     *ppVector = NULL;
00101 
00102     return 0;
00103 }
00104 
00105 int vectorAdd(LPVECTOR pVector, void * data)
00106 {
00107     int rc = 0;
00108 
00109     IILC_TRACE_ENTRY(IILC_MODULE, T_vectorAdd);
00110     traceDebug(IILC_TRACE_CONTEXT, "pVector %p, data %p", pVector, data);
00111 
00112     if (pVector->nCapacity == pVector->nSize) {
00113 
00114         void ** pNewArray = NULL;
00115 
00116         /* Create a new array */
00117         pNewArray = (void **) realloc((void *) pVector->pData, pVector->nCapacity * 2);
00118         if (pNewArray == NULL) {
00119             rc = ERR_MEM_ALLOC_FAILED;
00120             traceError(IILC_TRACE_CONTEXT, "Memory allocation failed");
00121             goto end_of_function;
00122         }
00123 
00124         /* Clear out new data region */
00125         memset(pNewArray[pVector->nCapacity], 0, pVector->nCapacity * sizeof(void *));
00126 
00127         /* Update capacity */
00128         pVector->nCapacity = pVector->nCapacity * 2;
00129 
00130         /* Remember where new data lies */
00131         pVector->pData = pNewArray;
00132     }
00133 
00134     /* Now easy to assign new data */
00135     pVector->pData[pVector->nSize] = data;
00136 
00137     /* Update size */
00138     pVector->nSize = pVector->nSize + 1;
00139 
00140 end_of_function:
00141 
00142     IILC_TRACE_EXIT_RC(rc);
00143     return rc;
00144 }
00145 
00146 int vectorRemove(LPVECTOR pVector, void * data)
00147 {
00148     return 0;
00149 }
00150 
00151 int vectorGetSize(LPVECTOR pVector, int * pnSize)
00152 {
00153     *pnSize = pVector->nSize;
00154 
00155     return 0;
00156 }
00157 
00158 int vectorGetElementAt(LPVECTOR pVector, int nIndex, void ** pData)
00159 {
00160     int rc = 0;
00161 
00162     if (nIndex < 0 || nIndex > pVector->nSize) {
00163         rc = -1;
00164     }
00165     else {
00166         *pData = pVector->pData[nIndex];
00167     }
00168 
00169     return 0;
00170 }
00171 
00172 int vectorSetElementAt(LPVECTOR pVector, int nIndex, void * pData)
00173 {
00174     int rc = 0;
00175     int nNewCapacity = 0;
00176 
00177     IILC_TRACE_ENTRY(IILC_MODULE, T_vectorSetElementAt);
00178     traceDebug(IILC_TRACE_CONTEXT, "pVector %p, nIndex %d, pData %p", pVector, nIndex, pData);
00179 
00180     nNewCapacity = pVector->nCapacity;
00181     while (nIndex > nNewCapacity) {
00182         nNewCapacity *= 2;
00183     }
00184 
00185     /* Resize array as necessary */
00186     if (nNewCapacity != pVector->nCapacity) {
00187 
00188         void ** pNewArray = NULL;
00189 
00190         /* Create a new array */
00191         pNewArray = (void **) realloc((void *) pVector->pData, nNewCapacity);
00192         if (pNewArray == NULL) {
00193             rc = ERR_MEM_ALLOC_FAILED;
00194             traceError(IILC_TRACE_CONTEXT, "Memory allocation failed");
00195             goto end_of_function;
00196         }
00197 
00198         /* Clear out new data region */
00199         memset(pNewArray[pVector->nCapacity], 0, pVector->nCapacity * sizeof(void *));
00200 
00201         /* Remember where new data lies */
00202         pVector->pData = pNewArray;
00203 
00204         /* Update capacity */
00205         pVector->nCapacity = nNewCapacity;
00206     }
00207 
00208     /* Now easy to assign new data */
00209     pVector->pData[nIndex] = pData;
00210 
00211     /* Update size */
00212     pVector->nSize = pVector->nSize + 1;
00213 
00214 end_of_function:
00215 
00216     IILC_TRACE_EXIT_RC(rc);
00217     return rc;
00218 }
00219 
00220 

Generated on Mon Jul 17 01:36:11 2006 for IILC by  doxygen 1.4.6