Home | History | Annotate | Download | only in src
      1 /*************************************************************************/
      2 /* module:         XLT Decoder Stack                                     */
      3 /* file:           XLTUtilStack.c                                        */
      4 /* target system:  all                                                   */
      5 /* target OS:      all                                                   */
      6 /*************************************************************************/
      7 
      8 /*
      9  * Copyright Notice
     10  * Copyright (c) Ericsson, IBM, Lotus, Matsushita Communication
     11  * Industrial Co., Ltd., Motorola, Nokia, Openwave Systems, Inc.,
     12  * Palm, Inc., Psion, Starfish Software, Symbian, Ltd. (2001).
     13  * All Rights Reserved.
     14  * Implementation of all or part of any Specification may require
     15  * licenses under third party intellectual property rights,
     16  * including without limitation, patent rights (such a third party
     17  * may or may not be a Supporter). The Sponsors of the Specification
     18  * are not responsible and shall not be held responsible in any
     19  * manner for identifying or failing to identify any or all such
     20  * third party intellectual property rights.
     21  *
     22  * THIS DOCUMENT AND THE INFORMATION CONTAINED HEREIN ARE PROVIDED
     23  * ON AN "AS IS" BASIS WITHOUT WARRANTY OF ANY KIND AND ERICSSON, IBM,
     24  * LOTUS, MATSUSHITA COMMUNICATION INDUSTRIAL CO. LTD, MOTOROLA,
     25  * NOKIA, PALM INC., PSION, STARFISH SOFTWARE AND ALL OTHER SYNCML
     26  * SPONSORS DISCLAIM ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING
     27  * BUT NOT LIMITED TO ANY WARRANTY THAT THE USE OF THE INFORMATION
     28  * HEREIN WILL NOT INFRINGE ANY RIGHTS OR ANY IMPLIED WARRANTIES OF
     29  * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT
     30  * SHALL ERICSSON, IBM, LOTUS, MATSUSHITA COMMUNICATION INDUSTRIAL CO.,
     31  * LTD, MOTOROLA, NOKIA, PALM INC., PSION, STARFISH SOFTWARE OR ANY
     32  * OTHER SYNCML SPONSOR BE LIABLE TO ANY PARTY FOR ANY LOSS OF
     33  * PROFITS, LOSS OF BUSINESS, LOSS OF USE OF DATA, INTERRUPTION OF
     34  * BUSINESS, OR FOR DIRECT, INDIRECT, SPECIAL OR EXEMPLARY, INCIDENTAL,
     35  * PUNITIVE OR CONSEQUENTIAL DAMAGES OF ANY KIND IN CONNECTION WITH
     36  * THIS DOCUMENT OR THE INFORMATION CONTAINED HEREIN, EVEN IF ADVISED
     37  * OF THE POSSIBILITY OF SUCH LOSS OR DAMAGE.
     38  *
     39  * The above notice and this paragraph must be included on all copies
     40  * of this document that are made.
     41  *
     42  */
     43 
     44 /**
     45  * A simple array-based stack implementation.
     46  */
     47 
     48 /*************************************************************************/
     49 /* Definitions                                                           */
     50 /*************************************************************************/
     51 
     52 #include "xltdeccom.h"
     53 #include "xltutilstack.h"
     54 
     55 #include <smlerr.h>
     56 
     57 #include <libmem.h>
     58 
     59 struct ArrayStack_s;
     60 typedef struct ArrayStack_s *ArrayStackPtr_t, ArrayStack_t;
     61 struct ArrayStack_s
     62 {
     63     /* public */
     64     Ret_t (*top)(const XltUtilStackPtr_t, XltUtilStackItem_t *);
     65     Ret_t (*pop)(XltUtilStackPtr_t, XltUtilStackItem_t *);
     66     Ret_t (*push)(XltUtilStackPtr_t, const XltUtilStackItem_t);
     67     Ret_t (*destroy)(XltUtilStackPtr_t);
     68 
     69     /* private */
     70     Long_t topidx;          // index of the top of the stack
     71     Long_t size;            // size of the stack (multiple of chunksize)
     72     Long_t chunksize;       // size of memory chunks allocated at a time
     73     XltUtilStackItem_t *array;     // the stack itself
     74 };
     75 
     76 static Ret_t _top(const XltUtilStackPtr_t, XltUtilStackItem_t *);
     77 static Ret_t _pop(XltUtilStackPtr_t, XltUtilStackItem_t *);
     78 static Ret_t _push(XltUtilStackPtr_t, const XltUtilStackItem_t);
     79 static Ret_t _destroy(XltUtilStackPtr_t);
     80 
     81 /*************************************************************************/
     82 /* External Functions                                                    */
     83 /*************************************************************************/
     84 
     85 Ret_t
     86 xltUtilCreateStack(XltUtilStackPtr_t *ppStack, const Long_t size)
     87 {
     88     ArrayStackPtr_t pStack;
     89 
     90     if (size <= 0)
     91         return SML_ERR_WRONG_PARAM;
     92         if ((pStack = (ArrayStackPtr_t)smlLibMalloc(sizeof(ArrayStack_t))) == NULL) {
     93  		*ppStack = NULL;
     94            return SML_ERR_NOT_ENOUGH_SPACE;
     95  	}
     96 
     97     pStack->top = _top;
     98     pStack->pop = _pop;
     99     pStack->push = _push;
    100     pStack->destroy = _destroy;
    101     pStack->topidx = -1;
    102     pStack->size = size;
    103     pStack->chunksize = size;
    104     pStack->array = NULL;
    105     if ((pStack->array = (XltUtilStackItem_t*)smlLibMalloc(size * sizeof(XltUtilStackItem_t))) == NULL) {
    106  		*ppStack = NULL;
    107  		smlLibFree(pStack);
    108         return SML_ERR_NOT_ENOUGH_SPACE;
    109  	}
    110 
    111     *ppStack = (XltUtilStackPtr_t)pStack;
    112 
    113 
    114 
    115     return SML_ERR_OK;
    116 }
    117 
    118 /*************************************************************************/
    119 /* Internal Functions                                                    */
    120 /*************************************************************************/
    121 
    122 static Ret_t
    123 _top(const XltUtilStackPtr_t pStack, XltUtilStackItem_t *itemPtr)
    124 {
    125     ArrayStackPtr_t pStackPriv = (ArrayStackPtr_t)pStack;
    126 
    127     if (pStackPriv->topidx == -1)
    128         return SML_ERR_WRONG_USAGE;
    129 
    130     *itemPtr = pStackPriv->array[pStackPriv->topidx];
    131 
    132     return SML_ERR_OK;
    133 }
    134 
    135 static Ret_t
    136 _pop(XltUtilStackPtr_t pStack, XltUtilStackItem_t *itemPtr)
    137 {
    138     ArrayStackPtr_t pStackPriv = (ArrayStackPtr_t)pStack;
    139     XltUtilStackItem_t item;
    140 
    141     if (pStackPriv->topidx == -1)
    142         return SML_ERR_WRONG_USAGE;
    143 
    144     item = pStackPriv->array[pStackPriv->topidx];
    145     pStackPriv->topidx--;
    146 
    147     if ((pStackPriv->topidx >= 0) &&
    148             (pStackPriv->topidx < pStackPriv->size - pStackPriv->chunksize)) {
    149         Long_t newsize;
    150         XltUtilStackItem_t *newarray;
    151 
    152         newsize = pStackPriv->size - pStackPriv->chunksize;
    153         if ((newarray = (XltUtilStackItem_t*)smlLibRealloc(pStackPriv->array,
    154                         newsize * sizeof(XltUtilStackItem_t))) != NULL) {
    155             pStackPriv->size = newsize;
    156             pStackPriv->array = newarray;
    157         } else {
    158             return SML_ERR_NOT_ENOUGH_SPACE;
    159         }
    160     }
    161 
    162     *itemPtr = item;
    163 
    164     return SML_ERR_OK;
    165 }
    166 
    167 static Ret_t
    168 _push(XltUtilStackPtr_t pStack, const XltUtilStackItem_t item)
    169 {
    170     ArrayStackPtr_t pStackPriv = (ArrayStackPtr_t)pStack;
    171 
    172     if (pStackPriv->topidx == pStackPriv->size - 1) {
    173         Long_t newsize;
    174         XltUtilStackItem_t *newarray;
    175 
    176         newsize = pStackPriv->size + pStackPriv->chunksize;
    177         if ((newarray = (XltUtilStackItem_t*)smlLibRealloc(pStackPriv->array,
    178                         newsize * sizeof(XltUtilStackItem_t))) != NULL) {
    179             pStackPriv->size = newsize;
    180             pStackPriv->array = newarray;
    181         } else {
    182             return SML_ERR_NOT_ENOUGH_SPACE;
    183         }
    184     }
    185 
    186     pStackPriv->topidx++;
    187     pStackPriv->array[pStackPriv->topidx] = item;
    188 
    189     return SML_ERR_OK;
    190 }
    191 
    192 static Ret_t
    193 _destroy(XltUtilStackPtr_t pStack)
    194 {
    195     ArrayStackPtr_t pStackPriv;
    196 
    197     if (pStack == NULL)
    198         return SML_ERR_OK;
    199 
    200     pStackPriv = (ArrayStackPtr_t)pStack;
    201 
    202     smlLibFree(pStackPriv->array);
    203     smlLibFree(pStackPriv);
    204     return SML_ERR_OK;
    205 }
    206