/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License.  You may obtain a copy of the License at
 * 
 *   http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */

/*-------------------------------------------------------------------------
 *
 * cdbptrbuf.h
 *    a container for pointers, layered on CdbPtrBuf
 *
 *
 *-------------------------------------------------------------------------
 */
#ifndef CDBPTRBUF_H
#define CDBPTRBUF_H

#include "cdb/cdbcellbuf.h"             /* CdbCellBuf */

typedef void   *CdbPtrBuf_Ptr;          /* type of pointer held by CdbPtrBuf */


typedef struct CdbPtrBuf
{
    CdbCellBuf              cellbuf;
} CdbPtrBuf;

typedef struct CdbPtrBuf_Iterator
{
    CdbCellBuf_Iterator     it;
} CdbPtrBuf_Iterator;

/*-------------------------------------------------------------------------
 *                    Initialize/Reset caller's CdbPtrBuf
 *-------------------------------------------------------------------------
 */

/*
 * CdbPtrBuf_InitEasy
 *
 * Initialize caller's CdbPtrBuf struct (easy-to-call version).
 *
 * 'ptrbuf' is the area to be initialized as a CdbPtrBuf.
 */
static inline void
CdbPtrBuf_InitEasy(CdbPtrBuf *ptrbuf)
{
    CdbCellBuf_InitEasy(&ptrbuf->cellbuf, sizeof(CdbPtrBuf_Ptr));
}

/*
 * CdbPtrBuf_Init
 *
 * Initialize caller's CdbPtrBuf struct.
 *
 * 'ptrbuf' is the area to be initialized as a CdbPtrBuf.
 * 'initial_cell_area' is an optional memory area, properly aligned, where
 *      the first few pointers can be stored.  It must be nearby the CdbPtrBuf
 *      itself, typically in the same struct or local variable stack frame.
 *      This allows a small number of cells to be managed with good locality
 *      and no palloc/pfree.  If NULL, memory is allocated from 'context'
 *      when needed.
 * 'num_initial_cells' is the exact number of cells in the initial_cell_area.
 * 'num_cells_expand' is the suggested number of ptr cells to be allocated
 *      whenever additional memory is needed.  The actual number will be
 *      rounded to fully utilize a power-of-2.  However, no expansion is
 *      done if num_cells_expand is zero; instead, after the initial cells
 *      are exhausted an error is raised.
 * 'context' is the memory context from which to allocate chunks of space
 *      for additional cells when there is no more room in initial_cell_area.
 *      If NULL, the CurrentMemoryContext is used.
 */
static inline void
CdbPtrBuf_Init(CdbPtrBuf       *ptrbuf,
               CdbPtrBuf_Ptr   *initial_cell_area,
               int              num_initial_cells,
               int              num_cells_expand,
               MemoryContext    context)
{
    CdbCellBuf_Init(&ptrbuf->cellbuf,
                    sizeof(*initial_cell_area),
                    initial_cell_area,
                    num_initial_cells,
                    num_cells_expand,
                    context);
}

/*
 * CdbPtrBuf_Reset
 *
 * Free memory held by a ptrbuf.  Does not free the CdbPtrBuf struct.
 *
 * Should be used to clean up a ptrbuf initialized by CdbPtrBuf_Init().
 * (NB: An acceptable alternative for cleaning up would be to destroy or
 * reset the associated MemoryContext.)
 *
 * Iterators (CdbPtrBuf_Iterator) become invalid when their ptrbuf is
 * reset; afterward the caller should abandon or reinitialize them.
 */
static inline void
CdbPtrBuf_Reset(CdbPtrBuf *ptrbuf)
{
    CdbCellBuf_Reset(&ptrbuf->cellbuf);
}

/*-------------------------------------------------------------------------
 *              Create/Destroy dynamically allocated CdbPtrBuf
 *-------------------------------------------------------------------------
 */

/*
 * CdbPtrBuf_CreateWrap
 *
 * Returns zeroed, newly allocated memory for a structure of given size,
 * with a CdbPtrBuf initialized at a given offset within the structure,
 * and followed by space for initial cells.
 *
 * 'sizeof_outer_struct' is the size of the struct in which the CdbPtrBuf is
 *      embedded.
 * 'offsetof_ptrbuf_in_struct' is the offset of the CdbPtrBuf within that.
 * 'num_initial_cells' is the suggested number of ptr cells to be created
 *      immediately following the struct.  This allows a small number
 *      of cells to be managed with good locality and no palloc/pfree.
 *      If NULL, all cells are stored in chunks allocated from 'context'.
 *      The actual number will be rounded up to minimize wasted space.
 * 'num_cells_expand' is the suggested number of ptr cells to be allocated
 *      whenever additional memory is needed.  The actual number will be
 *      rounded to fully utilize a power-of-2 chunk assuming 'context'
 *      is a standard memory context as implemented by aset.c.  However, no
 *      expansion is done if num_cells_expand is zero; instead, after the
 *      initial cells are exhausted an error is raised.
 * 'context' is the memory context from which the CdbPtrBuf and cells are
 *      to be allocated.  If NULL, the CurrentMemoryContext is used.
 */
static inline void *
CdbPtrBuf_CreateWrap(size_t         sizeof_outer_struct,
                     size_t         offsetof_ptrbuf_in_struct,
                     int            num_initial_cells,
                     int            num_cells_expand,
                     MemoryContext  context)
{
    Assert(offsetof_ptrbuf_in_struct >= 0 &&
           offsetof_ptrbuf_in_struct + sizeof(CdbPtrBuf) <= sizeof_outer_struct);

    return CdbCellBuf_CreateWrap(sizeof_outer_struct,
                                 offsetof_ptrbuf_in_struct + offsetof(CdbPtrBuf, cellbuf),
                                 sizeof(CdbPtrBuf_Ptr),
                                 num_initial_cells,
                                 num_cells_expand,
                                 context);
}

/*
 * CdbPtrBuf_Create
 *
 * Returns a newly allocated CdbPtrBuf.
 *
 * 'num_initial_cells' is the number of ptr cells to be created immediately
 *      following the CdbPtrBuf.  This allows a small number of cells to be
 *      managed with good locality and no palloc/pfree.  If NULL, all cells
 *      are stored in chunks allocated from 'context'.
 *      The actual number will be rounded up to minimize wasted space.
 * 'num_cells_expand' is the suggested number of ptr cells to be allocated
 *      whenever additional memory is needed.  The actual number will be
 *      rounded to fully utilize a power-of-2 chunk assuming 'context'
 *      is a standard memory context as implemented by aset.c.  However, no
 *      expansion is done if num_cells_expand is zero; instead, after the
 *      initial cells are exhausted an error is raised.
 * 'context' is the memory context from which the CdbPtrBuf and cells are
 *      to be allocated.  If NULL, the CurrentMemoryContext is used.
 */
static inline CdbPtrBuf *
CdbPtrBuf_Create(int            num_initial_cells,
                 int            num_cells_expand,
                 MemoryContext  context)
{
    return (CdbPtrBuf *)CdbCellBuf_CreateWrap(sizeof(CdbPtrBuf),
                                              offsetof(CdbPtrBuf, cellbuf),
                                              sizeof(CdbPtrBuf_Ptr),
                                              num_initial_cells,
                                              num_cells_expand,
                                              context);
}

/*
 * CdbPtrBuf_Destroy
 *
 * Free a CdbPtrBuf struct allocated by CdbPtrBuf_Create().
 *
 * Do not use this to free a cellbuf allocated by CdbPtrBuf_CreateWrap()
 * unless offsetof_ptrbuf_in_struct == 0.
 *
 * NB: CdbPtrBuf_Reset() can be used to free the memory owned by a ptrbuf
 * without freeing the CdbPtrBuf struct itself.  That is safe for all
 * ptrbufs.
 *
 * (NB: An acceptable alternative for cleaning up would be to destroy or
 * reset the associated MemoryContext.)
 */
static inline void
CdbPtrBuf_Destroy(CdbPtrBuf *ptrbuf)
{
    CdbCellBuf_Destroy((CdbCellBuf *)ptrbuf);
}

/*-------------------------------------------------------------------------
 *                            Examine ptrbuf state
 *-------------------------------------------------------------------------
 */

/*
 * CdbPtrBuf_Context
 *
 * Returns the memory context used for allocating additional bunches of cells.
 */
static inline MemoryContext
CdbPtrBuf_Context(const CdbCellBuf *cellbuf)
{
    return CdbCellBuf_Context(cellbuf);
}                               /* CdbPtrBuf_Context */

/*
 * CdbPtrBuf_IsEmpty
 *
 * Returns true if ptrbuf is empty.
 */
static inline bool
CdbPtrBuf_IsEmpty(const CdbPtrBuf *ptrbuf)
{
    return CdbCellBuf_IsEmpty(&ptrbuf->cellbuf);
}                               /* CdbPtrBuf_IsEmpty */

/*
 * CdbPtrBuf_IsOk
 *
 * Returns true if the ptrbuf passes a consistency check.
 */
static inline bool
CdbPtrBuf_IsOk(const CdbPtrBuf *ptrbuf)
{
    return CdbCellBuf_IsOk(&ptrbuf->cellbuf, sizeof(CdbPtrBuf_Ptr));
}                               /* CdbPtrBuf_IsOk */

/*
 * CdbPtrBuf_FirstCell
 *
 * Returns a pointer to the head cell, or NULL if the ptrbuf is empty.
 */
static inline CdbPtrBuf_Ptr *
CdbPtrBuf_FirstCell(CdbPtrBuf *ptrbuf)
{
    return (CdbPtrBuf_Ptr *)CdbCellBuf_FirstCell(&ptrbuf->cellbuf);
}                               /* CdbPtrBuf_FirstCell */

/*
 * CdbPtrBuf_LastCell
 *
 * Returns a pointer to the tail cell, or NULL if the ptrbuf is empty.
 */
static inline CdbPtrBuf_Ptr *
CdbPtrBuf_LastCell(CdbPtrBuf *ptrbuf)
{
    return (CdbPtrBuf_Ptr *)CdbCellBuf_LastCell(&ptrbuf->cellbuf);
}                               /* CdbPtrBuf_LastCell */

/*
 * CdbPtrBuf_First
 *
 * Returns contents of the head cell, or NULL if the ptrbuf is empty.
 *
 * Note that a NULL return value is ambiguous: it could be that the ptrbuf
 * is empty, or that the requested cell contains NULL.
 */
static inline CdbPtrBuf_Ptr
CdbPtrBuf_First(CdbPtrBuf *ptrbuf)
{
    CdbPtrBuf_Ptr  *pp = CdbPtrBuf_FirstCell(ptrbuf);

    return pp ? *pp : NULL;
}                               /* CdbPtrBuf_First */

/*
 * CdbPtrBuf_Last
 *
 * Returns contents of the tail cell, or NULL if the ptrbuf is empty.
 *
 * Note that a NULL return value is ambiguous: it could be that the ptrbuf
 * is empty, or that the requested cell contains NULL.
 */
static inline CdbPtrBuf_Ptr
CdbPtrBuf_Last(CdbPtrBuf *ptrbuf)
{
    CdbPtrBuf_Ptr  *pp = CdbPtrBuf_LastCell(ptrbuf);

    return pp ? *pp : NULL;
}                               /* CdbPtrBuf_Last */

/*
 * CdbPtrBuf_Length
 *
 * Returns the number of ptrs in use.
 */
static inline unsigned
CdbPtrBuf_Length(CdbPtrBuf *ptrbuf)
{
    return CdbCellBuf_Length(&ptrbuf->cellbuf);
}                               /* CdbPtrBuf_Length */

/*-------------------------------------------------------------------------
 *                              Cell operations
 *-------------------------------------------------------------------------
 */

/*
 * CdbPtrBuf_Append
 *
 * Append an item at tail of ptrbuf.  Returns pointer to the new cell.
 */
static inline CdbPtrBuf_Ptr *
CdbPtrBuf_Append(CdbPtrBuf *ptrbuf, CdbPtrBuf_Ptr item)
{
    CdbPtrBuf_Ptr  *pp = (CdbPtrBuf_Ptr *)CdbCellBuf_AppendCell(&ptrbuf->cellbuf);

    *pp = item;
    return pp;
}                               /* CdbPtrBuf_Append */

/*
 * CdbPtrBuf_Pop
 *
 * Remove last item from tail of ptrbuf.  Returns the item, or NULL if
 * ptrbuf is empty.
 */
static inline CdbPtrBuf_Ptr
CdbPtrBuf_Pop(CdbPtrBuf *ptrbuf)
{
    CdbPtrBuf_Ptr  *pp = (CdbPtrBuf_Ptr *)CdbCellBuf_PopCell(&ptrbuf->cellbuf);

    return pp ? *pp : NULL;
}                               /* CdbPtrBuf_Pop */

/*
 * CdbPtrBuf_PopCell
 *
 * Remove last item from tail of ptrbuf.  Returns pointer to the cell
 * containing the item; it remains valid until the next append, pop,
 * reset or destroy.  Returns NULL if ptrbuf is empty.
 */
static inline CdbPtrBuf_Ptr *
CdbPtrBuf_PopCell(CdbPtrBuf *ptrbuf)
{
    return (CdbPtrBuf_Ptr *)CdbCellBuf_PopCell(&ptrbuf->cellbuf);
}                               /* CdbPtrBuf_PopCell */


/*-------------------------------------------------------------------------
 *                             CdbPtrBuf_Iterator
 *-------------------------------------------------------------------------
 */

/*
 * CdbPtrBuf_Iterator_Init
 *
 * Initializes caller's CdbPtrBuf_Iterator struct, positioning the iterator
 * before the first cell.
 */
static inline void
CdbPtrBuf_Iterator_Init(CdbPtrBuf_Iterator *it, CdbPtrBuf *ptrbuf)
{
    CdbCellBuf_Iterator_Init(&it->it, &ptrbuf->cellbuf);
}                               /* CdbPtrBuf_Iterator_Init */

/*
 * CdbPtrBuf_Iterator_InitToEnd
 *
 * Initializes caller's CdbPtrBuf_Iterator struct, positioning the iterator
 * after the last cell.  Equivalent to:
 *
 *      CdbPtrBuf_Iterator_Init(it, ptrbuf);
 *      CdbPtrBuf_Iterator_SetPos(it, CdbPtrBuf_Length(ptrbuf));
 */
static inline void
CdbPtrBuf_Iterator_InitToEnd(CdbPtrBuf_Iterator *it, CdbPtrBuf *ptrbuf)
{
    CdbCellBuf_Iterator_InitToEnd(&it->it, &ptrbuf->cellbuf);
}                               /* CdbPtrBuf_Iterator_InitToEnd */


/*
 * CdbPtrBuf_Iterator_NextCell
 *
 * If iterator 'it' is positioned before a cell, returns a pointer to the cell
 * and advances the iterator past that cell.  Else returns NULL and leaves the
 * iterator unchanged.
 *
 * This can be used to modify the values stored in the ptrbuf.  It can also
 * be used in case there are NULL pointers in the ptrbuf because the return
 * value is non-NULL until the end of iteration.
 *
 * NB: The iterator will reach new items added by CdbPtrBuf_Append() during
 * or after the traversal.  Even when the end has been reached, the caller
 * can add more items and continue calling CdbPtrBuf_Iterator_Next() or
 * CdbPtrBuf_Iterator_NextCell() to retrieve them.
 */
static inline CdbPtrBuf_Ptr *
CdbPtrBuf_Iterator_NextCell(CdbPtrBuf_Iterator *it)
{
    return (CdbPtrBuf_Ptr *)CdbCellBuf_Iterator_NextCell(&it->it);
}                               /* CdbPtrBuf_Iterator_NextCell */

/*
 * CdbPtrBuf_Iterator_Next
 *
 * If iterator 'it' is positioned before a cell, returns the contents of the
 * cell and advances the iterator past that cell.  Else returns NULL and leaves
 * the iterator unchanged.
 *
 * Note that a NULL return value is ambiguous if there are NULL values in the
 * ptrbuf: the caller can't tell whether the result is an actual NULL ptr value
 * or the end of iteration.  Suggested solutions: (a) store only non-NULL
 * values in the ptrbuf; or (b) use CdbPtrBuf_Iterator_NextCell() instead of
 * CdbPtrBuf_Iterator_Next(); or (c) use CdbPtrBuf_Iterator_AtEnd() to detect
 * end of iteration; or (d) iterate from [0..CdbPtrBuf_Iterator_Length()-1] or
 * [0..CdbPtrBuf_Length()-1].
 *
 * NB: The iterator will reach new items added by CdbPtrBuf_Append() during
 * or after the traversal.  Even when the end has been reached, the caller
 * can add more items and continue calling CdbPtrBuf_Iterator_Next() or
 * CdbPtrBuf_Iterator_NextCell() to retrieve them.
 */
static inline CdbPtrBuf_Ptr
CdbPtrBuf_Iterator_Next(CdbPtrBuf_Iterator *it)
{
    CdbPtrBuf_Ptr  *pp = CdbPtrBuf_Iterator_NextCell(it);

    return pp ? *pp : NULL;
}                               /* CdbPtrBuf_Iterator_Next */

/*
 * CdbPtrBuf_Iterator_PrevCell
 *
 * If iterator 'it' is positioned after a cell, returns a pointer to the
 * cell and repositions the iterator before that cell.  Else returns NULL
 * and leaves the iterator unchanged.
 *
 * This can be used to modify the values stored in the ptrbuf.  It can also
 * be used in case there are NULL pointers in the ptrbuf because the return
 * value is non-NULL until the end of iteration.
 */
static inline CdbPtrBuf_Ptr *
CdbPtrBuf_Iterator_PrevCell(CdbPtrBuf_Iterator *it)
{
    return (CdbPtrBuf_Ptr *)CdbCellBuf_Iterator_PrevCell(&it->it);
}                               /* CdbPtrBuf_Iterator_PrevCell */

/*
 * CdbPtrBuf_Iterator_Prev
 *
 * If iterator 'it' is positioned after a cell, returns the contents of the
 * cell and repositions the iterator before that cell.  Else returns NULL
 * and leaves the iterator unchanged.
 *
 * Note that a NULL return value is ambiguous if there are NULL values in the
 * ptrbuf: the caller can't tell whether the result is an actual NULL ptr value
 * or the end of iteration.  Suggested solutions: (a) store only non-NULL
 * values in the ptrbuf; or (b) use CdbPtrBuf_Iterator_NextCell() instead of
 * CdbPtrBuf_Iterator_Next(); or (c) use CdbPtrBuf_Iterator_AtEnd() to detect
 * end of iteration; or (d) iterate from [0..CdbPtrBuf_Iterator_Length()-1] or
 * [0..CdbPtrBuf_Length()-1].
 */
static inline CdbPtrBuf_Ptr
CdbPtrBuf_Iterator_Prev(CdbPtrBuf_Iterator *it)
{
    CdbPtrBuf_Ptr  *pp = CdbPtrBuf_Iterator_PrevCell(it);

    return pp ? *pp : NULL;
}                               /* CdbPtrBuf_Iterator_Prev */

/*
 * CdbPtrBuf_Iterator_CellAt
 *
 * Returns a pointer to the cell at a specified position relative to the
 * iterator's current position; or NULL if the specified position would
 * be out of bounds.  Does not affect the position or state of the iterator.
 *
 * relCellIndex == 0 returns the same value that CdbPtrBuf_Iterator_NextCell
 * would return, but does not advance the iterator.
 *
 * relCellIndex == -1 returns the same value that CdbPtrBuf_Iterator_PrevCell
 * would return, without repositioning the iterator.
 *
 * This can be used to modify the values stored in the ptrbuf.  It can also
 * be used in case there are NULL pointers in the ptrbuf because the return
 * value is non-NULL for relCellIndex in bounds.
 */
static inline CdbPtrBuf_Ptr *
CdbPtrBuf_Iterator_CellAt(CdbPtrBuf_Iterator *it, long relCellIndex)
{
    return (CdbPtrBuf_Ptr *)CdbCellBuf_Iterator_CellAt(&it->it, relCellIndex);
}                               /* CdbPtrBuf_Iterator_CellAt */

/*
 * CdbPtrBuf_Iterator_Peek
 *
 * Returns the contents of the cell at a specified position relative to the
 * iterator's current position; or NULL if the specified position would
 * be out of bounds.  Does not affect the position or state of the iterator.
 *
 * relCellIndex == 0 returns the same value that CdbPtrBuf_Iterator_Next
 * would return, but does not advance the iterator.
 *
 * relCellIndex == -1 returns the same value that CdbPtrBuf_Iterator_Prev
 * would return, without repositioning the iterator.
 *
 * Note that a NULL return value is ambiguous if there are NULL values in the
 * ptrbuf: the caller can't tell whether the result is an actual NULL ptr value
 * or an indication that relCellIndex is out of bounds.  If this is a concern,
 * you can use CdbPtrBuf_Iterator_CellAt instead of CdbPtrBuf_Iterator_Peek.
 */
static inline CdbPtrBuf_Ptr
CdbPtrBuf_Iterator_Peek(CdbPtrBuf_Iterator *it, long relCellIndex)
{
    CdbPtrBuf_Ptr  *pp = CdbPtrBuf_Iterator_CellAt(it, relCellIndex);

    return pp ? *pp : NULL;
}                               /* CdbPtrBuf_Iterator_Peek */


/*
 * CdbPtrBuf_Iterator_Poke
 *
 * Stores 'item' into the cell at a specified position relative to the
 * iterator's current position.  Does not affect the position or state
 * of the iterator.
 *
 * 'relCellIndex' must designate a cell within the cellbuf bounds:
 *  0 <= relCellIndex + CdbPtrBuf_Iterator_GetPos(it) < CdbPtrBuf_Iterator_Length(it)
 */
static inline void
CdbPtrBuf_Iterator_Poke(CdbPtrBuf_Iterator *it, long relCellIndex, CdbPtrBuf_Ptr item)
{
    *CdbPtrBuf_Iterator_CellAt(it, relCellIndex) = item;
}                               /* CdbPtrBuf_Iterator_Poke */


/*
 * CdbPtrBuf_Iterator_GetPos
 *
 * Returns the number of cells preceding the current iterator position.
 */
static inline long
CdbPtrBuf_Iterator_GetPos(const CdbPtrBuf_Iterator *it)
{
    return CdbCellBuf_Iterator_GetPos(&it->it);
}                               /* CdbPtrBuf_Iterator_GetPos */

/*
 * CdbPtrBuf_Iterator_SetPos
 *
 * Positions the iterator before the cell whose 0-based index is
 * 'nextCellIndex'.  The first call to CdbPtrBuf_Iterator_NextCell()
 * will return a pointer to the specified cell (or NULL if the starting
 * position equals the number of occupied cells.)
 *
 * If nextCellIndex == 0, positions the iterator before the first cell.
 * If nextCellIndex == CdbPtrBuf_Length(), positions the iterator after
 * the last cell.
 *
 * An internal error is raised if nextCellIndex is outside the bounds
 *      0 <= nextCellIndex <= CdbPtrBuf_Iterator_Length(it)
 */
static inline void
CdbPtrBuf_Iterator_SetPos(CdbPtrBuf_Iterator *it, long nextCellIndex)
{
    CdbCellBuf_Iterator_SetPos(&it->it, nextCellIndex);
}                               /* CdbCellBuf_Iterator_SetPos */

/*
 * CdbPtrBuf_Iterator_Length
 *
 * Returns the number of cells in the associated ptrbuf.
 */
static inline unsigned
CdbPtrBuf_Iterator_Length(CdbPtrBuf_Iterator *it)
{
    return CdbCellBuf_Iterator_Length(&it->it);
}                               /* CdbPtrBuf_Iterator_Length */

/*
 * CdbPtrBuf_Iterator_AtBegin
 *
 * Returns 'true' if iterator is positioned before the first cell or if
 * the ptrbuf is empty.  Returns 'false' if iterator has advanced.
 */
static inline bool
CdbPtrBuf_Iterator_AtBegin(const CdbPtrBuf_Iterator *it)
{
    return CdbCellBuf_Iterator_AtBegin(&it->it);
}                               /* CdbPtrBuf_Iterator_AtBegin */

/*
 * CdbPtrBuf_Iterator_AtEnd
 *
 * Returns 'true' if iterator is positioned after the last cell or if
 * the cellbuf is empty, i.e., if CdbCellBuf_Iterator_NextCell() would
 * return NULL.  Returns 'false' if iterator is positioned before a cell.
 */
static inline bool
CdbPtrBuf_Iterator_AtEnd(CdbPtrBuf_Iterator *it)
{
    return CdbCellBuf_Iterator_AtEnd(&it->it);
}                               /* CdbPtrBuf_Iterator_AtEnd */

#endif   /* CDBPTRBUF_H */
