Exemplo n.º 1
0
/* =============================================================================
 * TMnet_findDescendants
 * -- Contents of bitmapPtr set to 1 if descendants, else 0
 * -- Returns false if id is not root node (i.e., has cycle back id)
 * =============================================================================
 */
bool_t
TMnet_findDescendants (TM_ARGDECL
                       net_t* netPtr,
                       long id,
                       bitmap_t* descendantBitmapPtr,
                       queue_t* workQueuePtr)
{
    bool_t status;

    vector_t* nodeVectorPtr = netPtr->nodeVectorPtr;
    assert(descendantBitmapPtr->numBit == vector_getSize(nodeVectorPtr));

    PBITMAP_CLEARALL(descendantBitmapPtr);
    PQUEUE_CLEAR(workQueuePtr);

    {
        net_node_t* nodePtr = (net_node_t*)vector_at(nodeVectorPtr, id);
        list_t* childIdListPtr = nodePtr->childIdListPtr;
        list_iter_t it;
        TMLIST_ITER_RESET(&it, childIdListPtr);
        while (TMLIST_ITER_HASNEXT(&it, childIdListPtr)) {
            long childId = (long)TMLIST_ITER_NEXT(&it, childIdListPtr);
            status = PBITMAP_SET(descendantBitmapPtr, childId);
            assert(status);
            status = PQUEUE_PUSH(workQueuePtr, (void*)childId);
            assert(status);
        }
    }

    while (!PQUEUE_ISEMPTY(workQueuePtr)) {
        long childId = (long)PQUEUE_POP(workQueuePtr);
        if (childId == id) {
            queue_clear(workQueuePtr);
            return FALSE;
        }
        net_node_t* nodePtr = (net_node_t*)vector_at(nodeVectorPtr, childId);
        list_t* grandChildIdListPtr = nodePtr->childIdListPtr;
        list_iter_t it;
        TMLIST_ITER_RESET(&it, grandChildIdListPtr);
        while (TMLIST_ITER_HASNEXT(&it, grandChildIdListPtr)) {
            long grandChildId = (long)TMLIST_ITER_NEXT(&it, grandChildIdListPtr);
            if (!PBITMAP_ISSET(descendantBitmapPtr, grandChildId)) {
                status = PBITMAP_SET(descendantBitmapPtr, grandChildId);
                assert(status);
                status = PQUEUE_PUSH(workQueuePtr, (void*)grandChildId);
                assert(status);
            }
        }
    }

    return TRUE;
}
Exemplo n.º 2
0
/* =============================================================================
 * TMnet_findAncestors
 * -- Contents of bitmapPtr set to 1 if ancestor, else 0
 * -- Returns false if id is not root node (i.e., has cycle back id)
 * =============================================================================
 */
bool_t
TMnet_findAncestors (TM_ARGDECL
                     net_t* netPtr,
                     long id,
                     bitmap_t* ancestorBitmapPtr,
                     queue_t* workQueuePtr)
{
    bool_t status;

    vector_t* nodeVectorPtr = netPtr->nodeVectorPtr;
    assert(ancestorBitmapPtr->numBit == vector_getSize(nodeVectorPtr));

    PBITMAP_CLEARALL(ancestorBitmapPtr);
    PQUEUE_CLEAR(workQueuePtr);

    {
        net_node_t* nodePtr = (net_node_t*)vector_at(nodeVectorPtr, id);
        list_t* parentIdListPtr = nodePtr->parentIdListPtr;
        list_iter_t it;
        TMLIST_ITER_RESET(&it, parentIdListPtr);
        while (TMLIST_ITER_HASNEXT(&it, parentIdListPtr)) {
            long parentId = (long)TMLIST_ITER_NEXT(&it, parentIdListPtr);
            status = PBITMAP_SET(ancestorBitmapPtr, parentId);
            assert(status);
            status = PQUEUE_PUSH(workQueuePtr, (void*)parentId);
            assert(status);
        }
    }

    while (!PQUEUE_ISEMPTY(workQueuePtr)) {
        long parentId = (long)PQUEUE_POP(workQueuePtr);
        if (parentId == id) {
            PQUEUE_CLEAR(workQueuePtr);
            return FALSE;
        }
        net_node_t* nodePtr = (net_node_t*)vector_at(nodeVectorPtr, parentId);
        list_t* grandParentIdListPtr = nodePtr->parentIdListPtr;
        list_iter_t it;
        TMLIST_ITER_RESET(&it, grandParentIdListPtr);
        while (TMLIST_ITER_HASNEXT(&it, grandParentIdListPtr)) {
            long grandParentId = (long)TMLIST_ITER_NEXT(&it, grandParentIdListPtr);
            if (!PBITMAP_ISSET(ancestorBitmapPtr, grandParentId)) {
                status = PBITMAP_SET(ancestorBitmapPtr, grandParentId);
                assert(status);
                status = PQUEUE_PUSH(workQueuePtr, (void*)grandParentId);
                assert(status);
            }
        }
    }

    return TRUE;
}
Exemplo n.º 3
0
/* =============================================================================
 * TMhashtable_iter_next
 * =============================================================================
 */
void*
TMhashtable_iter_next (TM_ARGDECL
                       hashtable_iter_t* itPtr, hashtable_t* hashtablePtr)
{
    long bucket;
    long numBucket = hashtablePtr->numBucket;
    list_t** buckets = hashtablePtr->buckets;
    list_iter_t it = itPtr->it;
    void* dataPtr = NULL;

    for (bucket = itPtr->bucket; bucket < numBucket; /* inside body */) {
        list_t* chainPtr = hashtablePtr->buckets[bucket];
        if (TMLIST_ITER_HASNEXT(&it, chainPtr)) {
            pair_t* pairPtr = (pair_t*)TMLIST_ITER_NEXT(&it, chainPtr);
            dataPtr = pairPtr->secondPtr;
            break;
        }
        /* May use dummy bucket; see allocBuckets() */
        TMLIST_ITER_RESET(&it, buckets[++bucket]);
    }

    itPtr->bucket = bucket;
    itPtr->it = it;

    return dataPtr;
}
Exemplo n.º 4
0
/* =============================================================================
 * TMhashtable_iter_reset
 * =============================================================================
 */
void
TMhashtable_iter_reset (TM_ARGDECL
                        hashtable_iter_t* itPtr, hashtable_t* hashtablePtr)
{
    itPtr->bucket = 0;
    TMLIST_ITER_RESET(&(itPtr->it), hashtablePtr->buckets[0]);
}
Exemplo n.º 5
0
/* =============================================================================
 * customer_getBill
 * -- Returns total cost of reservations
 * =============================================================================
 */
__attribute__((transaction_safe)) long
customer_getBill (customer_t* customerPtr)
{
    long bill = 0;
    list_iter_t it;
    list_t* reservationInfoListPtr = customerPtr->reservationInfoListPtr;

    TMLIST_ITER_RESET(&it, reservationInfoListPtr);
    while (TMLIST_ITER_HASNEXT(&it, reservationInfoListPtr)) {
        reservation_info_t* reservationInfoPtr =
            (reservation_info_t*)TMLIST_ITER_NEXT(&it, reservationInfoListPtr);
        bill += reservationInfoPtr->price;
    }

    return bill;
}
Exemplo n.º 6
0
/* =============================================================================
 * manager_deleteCustomer
 * -- Delete this customer and associated reservations
 * -- If customer does not exist, returns success
 * -- Returns true on success, else false
 * =============================================================================
 */
bool
manager_deleteCustomer (TM_ARGDECL  manager_t* managerPtr, long customerId)
{
    customer_t* customerPtr;
    MAP_T* reservationTables[NUM_RESERVATION_TYPE];
    list_t* reservationInfoListPtr;
    list_iter_t it;
    bool status;

    customerPtr = (customer_t*)TMMAP_FIND(managerPtr->customerTablePtr, customerId);
    if (customerPtr == NULL) {
        return false;
    }

    reservationTables[RESERVATION_CAR] = managerPtr->carTablePtr;
    reservationTables[RESERVATION_ROOM] = managerPtr->roomTablePtr;
    reservationTables[RESERVATION_FLIGHT] = managerPtr->flightTablePtr;

    /* Cancel this customer's reservations */
    reservationInfoListPtr = customerPtr->reservationInfoListPtr;
    TMLIST_ITER_RESET(&it, reservationInfoListPtr);
    while (TMLIST_ITER_HASNEXT(&it, reservationInfoListPtr)) {
        reservation_info_t* reservationInfoPtr;
        reservation_t* reservationPtr;
        reservationInfoPtr =
            (reservation_info_t*)TMLIST_ITER_NEXT(&it, reservationInfoListPtr);
        reservationPtr =
            (reservation_t*)TMMAP_FIND(reservationTables[reservationInfoPtr->type],
                                     reservationInfoPtr->id);
        if (reservationPtr == NULL) {
            TM_RESTART();
        }
        status = RESERVATION_CANCEL(reservationPtr);
        if (!status) {
            TM_RESTART();
        }
        RESERVATION_INFO_FREE(reservationInfoPtr);
    }

    status = TMMAP_REMOVE(managerPtr->customerTablePtr, customerId);
    if (!status) {
        TM_RESTART();
    }
    CUSTOMER_FREE(customerPtr);

    return true;
}
Exemplo n.º 7
0
/* =============================================================================
 * customer_getBill
 * -- Returns total cost of reservations
 * =============================================================================
 */
long
customer_getBill (TM_ARGDECL  customer_t* customerPtr)
{
    long bill = 0;
    list_iter_t it;
    list_t* reservationInfoListPtr =
        (list_t*)TM_SHARED_READ_P(customerPtr->reservationInfoListPtr);

    TMLIST_ITER_RESET(&it, reservationInfoListPtr);
    while (TMLIST_ITER_HASNEXT(&it, reservationInfoListPtr)) {
        reservation_info_t* reservationInfoPtr =
            (reservation_info_t*)TMLIST_ITER_NEXT(&it, reservationInfoListPtr);
        bill += reservationInfoPtr->price;
    }

    return bill;
}
Exemplo n.º 8
0
/* =============================================================================
 * TMnet_hasEdge
 * =============================================================================
 */
bool_t
TMnet_hasEdge (TM_ARGDECL  net_t* netPtr, long fromId, long toId)
{
    vector_t* nodeVectorPtr = netPtr->nodeVectorPtr;
    net_node_t* childNodePtr = (net_node_t*)vector_at(nodeVectorPtr, toId);
    list_t* parentIdListPtr = childNodePtr->parentIdListPtr;

    list_iter_t it;
    TMLIST_ITER_RESET(&it, parentIdListPtr);
    while (TMLIST_ITER_HASNEXT(&it, parentIdListPtr)) {
        long parentId = (long)TMLIST_ITER_NEXT(&it, parentIdListPtr);
        if (parentId == fromId) {
            return TRUE;
        }
    }

    return FALSE;
}
Exemplo n.º 9
0
/* =============================================================================
 * TMnet_isPath
 * =============================================================================
 */
bool_t
TMnet_isPath (TM_ARGDECL
              net_t* netPtr,
              long fromId,
              long toId,
              bitmap_t* visitedBitmapPtr,
              queue_t* workQueuePtr)
{
    bool_t status;

    vector_t* nodeVectorPtr = netPtr->nodeVectorPtr;
    assert(visitedBitmapPtr->numBit == vector_getSize(nodeVectorPtr));

    PBITMAP_CLEARALL(visitedBitmapPtr);
    PQUEUE_CLEAR(workQueuePtr);

    status = PQUEUE_PUSH(workQueuePtr, (void*)fromId);
    assert(status);

    while (!PQUEUE_ISEMPTY(workQueuePtr)) {
        long id = (long)queue_pop(workQueuePtr);
        if (id == toId) {
            queue_clear(workQueuePtr);
            return TRUE;
        }
        status = PBITMAP_SET(visitedBitmapPtr, id);
        assert(status);
        net_node_t* nodePtr = (net_node_t*)vector_at(nodeVectorPtr, id);
        list_t* childIdListPtr = nodePtr->childIdListPtr;
        list_iter_t it;
        TMLIST_ITER_RESET(&it, childIdListPtr);
        while (TMLIST_ITER_HASNEXT(&it, childIdListPtr)) {
            long childId = (long)TMLIST_ITER_NEXT(&it, childIdListPtr);
            if (!PBITMAP_ISSET(visitedBitmapPtr, childId)) {
                status = PQUEUE_PUSH(workQueuePtr, (void*)childId);
                assert(status);
            }
        }
    }

    return FALSE;
}
Exemplo n.º 10
0
/* =============================================================================
 * hashtable_iter_hasNext
 * =============================================================================
 */
bool_t
TMhashtable_iter_hasNext (TM_ARGDECL
                          hashtable_iter_t* itPtr, hashtable_t* hashtablePtr)
{
    long bucket;
    long numBucket = hashtablePtr->numBucket;
    list_t** buckets = hashtablePtr->buckets;
    list_iter_t it = itPtr->it;

    for (bucket = itPtr->bucket; bucket < numBucket; /* inside body */) {
        list_t* chainPtr = buckets[bucket];
        if (TMLIST_ITER_HASNEXT(&it, chainPtr)) {
            return TRUE;
        }
        /* May use dummy bucket; see allocBuckets() */
        TMLIST_ITER_RESET(&it, buckets[++bucket]);
    }

    return FALSE;
}
Exemplo n.º 11
0
/* =============================================================================
 * TMdecoder_process
 * =============================================================================
 */
int_error_t
TMdecoder_process (TM_ARGDECL  decoder_t* decoderPtr, char* bytes, long numByte)
{
    bool_t status;

    /*
     * Basic error checking
     */

    if (numByte < (long)PACKET_HEADER_LENGTH) {
        return ERROR_SHORT;
    }

    packet_t* packetPtr = (packet_t*)bytes;
    long flowId      = packetPtr->flowId;
    long fragmentId  = packetPtr->fragmentId;
    long numFragment = packetPtr->numFragment;
    long length      = packetPtr->length;

    if (flowId < 0) {
        return ERROR_FLOWID;
    }

    if ((fragmentId < 0) || (fragmentId >= numFragment)) {
        return ERROR_FRAGMENTID;
    }

    if (length < 0) {
        return ERROR_LENGTH;
    }

#if 0
    /*
     * With the above checks, this one is redundant
     */
    if (numFragment < 1) {
        return ERROR_NUMFRAGMENT;
    }
#endif

    /*
     * Add to fragmented map for reassembling
     */

    if (numFragment > 1) {

        MAP_T* fragmentedMapPtr = decoderPtr->fragmentedMapPtr;
        list_t* fragmentListPtr =
            (list_t*)TMMAP_FIND(fragmentedMapPtr, (void*)flowId);

        if (fragmentListPtr == NULL) {

            fragmentListPtr = TMLIST_ALLOC(&decoder_comparator);
            assert(fragmentListPtr);
            status = TMLIST_INSERT(fragmentListPtr, (void*)packetPtr);
            assert(status);
            status = TMMAP_INSERT(fragmentedMapPtr,
                                  (void*)flowId,
                                  (void*)fragmentListPtr);
            assert(status);

        } else {

            list_iter_t it;
            TMLIST_ITER_RESET(&it, fragmentListPtr);
            assert(TMLIST_ITER_HASNEXT(&it, fragmentListPtr));
            packet_t* firstFragmentPtr =
                (packet_t*)TMLIST_ITER_NEXT(&it, fragmentListPtr);
            long expectedNumFragment = firstFragmentPtr->numFragment;

            if (numFragment != expectedNumFragment) {
                status = TMMAP_REMOVE(fragmentedMapPtr, (void*)flowId);
                assert(status);
                return ERROR_NUMFRAGMENT;
            }

            status = TMLIST_INSERT(fragmentListPtr, (void*)packetPtr);
            assert(status);

            /*
             * If we have all the fragments we can reassemble them
             */

            if (TMLIST_GETSIZE(fragmentListPtr) == numFragment) {

                long numByte = 0;
                long i = 0;
                TMLIST_ITER_RESET(&it, fragmentListPtr);
                while (TMLIST_ITER_HASNEXT(&it, fragmentListPtr)) {
                    packet_t* fragmentPtr =
                        (packet_t*)TMLIST_ITER_NEXT(&it, fragmentListPtr);
                 
		    if(fragmentPtr->flowId != flowId)
		      printf("fragflow %lx floId %lx\n", fragmentPtr->flowId, flowId);
		    assert(fragmentPtr->flowId == flowId);
                    if (fragmentPtr->fragmentId != i) {
                        status = TMMAP_REMOVE(fragmentedMapPtr, (void*)flowId);
                        assert(status);
                        return ERROR_INCOMPLETE; /* should be sequential */
                    }
                    numByte += fragmentPtr->length;
                    i++;
                }

                char* data = (char*)TM_MALLOC(numByte + 1);
                assert(data);
                data[numByte] = '\0';
                char* dst = data;
                TMLIST_ITER_RESET(&it, fragmentListPtr);
                while (TMLIST_ITER_HASNEXT(&it, fragmentListPtr)) {
                    packet_t* fragmentPtr =
                        (packet_t*)TMLIST_ITER_NEXT(&it, fragmentListPtr);
                    memcpy(dst, (void*)fragmentPtr->data, fragmentPtr->length);
                    dst += fragmentPtr->length;
                }
                assert(dst == data + numByte);

                decoded_t* decodedPtr = (decoded_t*)TM_MALLOC(sizeof(decoded_t));
                assert(decodedPtr);
                decodedPtr->flowId = flowId;
                decodedPtr->data = data;

                queue_t* decodedQueuePtr = decoderPtr->decodedQueuePtr;
                status = TMQUEUE_PUSH(decodedQueuePtr, (void*)decodedPtr);
                assert(status);

                TMLIST_FREE(fragmentListPtr);
                status = TMMAP_REMOVE(fragmentedMapPtr, (void*)flowId);
                assert(status);
            }

        }

    } else {

        /*
         * This is the only fragment, so it is ready
         */

        if (fragmentId != 0) {
            return ERROR_FRAGMENTID;
        }

        char* data = (char*)TM_MALLOC(length + 1);
        assert(data);
        data[length] = '\0';
        memcpy(data, (void*)packetPtr->data, length);

        decoded_t* decodedPtr = (decoded_t*)TM_MALLOC(sizeof(decoded_t));
        assert(decodedPtr);
        decodedPtr->flowId = flowId;
        decodedPtr->data = data;

        queue_t* decodedQueuePtr = decoderPtr->decodedQueuePtr;
        status = TMQUEUE_PUSH(decodedQueuePtr, (void*)decodedPtr);
        assert(status);

    }

    return ERROR_NONE;
}
Exemplo n.º 12
0
Arquivo: region.c Projeto: riclas/rstm
/* =============================================================================
 * TMgrowRegion
 * -- Return NULL if success, else pointer to encroached boundary
 * =============================================================================
 */
element_t*
TMgrowRegion (TM_ARGDECL
              element_t* centerElementPtr,
              region_t* regionPtr,
              mesh_t* meshPtr,
              MAP_T* edgeMapPtr)
{
  bool_t isBoundary = FALSE;

  if (element_getNumEdge(centerElementPtr) == 1) {
    isBoundary = TRUE;
  }

  list_t* beforeListPtr = regionPtr->beforeListPtr;
  list_t* borderListPtr = regionPtr->borderListPtr;
  queue_t* expandQueuePtr = regionPtr->expandQueuePtr;

  PLIST_CLEAR(beforeListPtr);
  PLIST_CLEAR(borderListPtr);
  PQUEUE_CLEAR(expandQueuePtr);

  coordinate_t centerCoordinate = TMelement_getNewPoint(TM_ARG centerElementPtr);
  coordinate_t* centerCoordinatePtr = &centerCoordinate;

  PQUEUE_PUSH(expandQueuePtr, (void*)centerElementPtr);
  while (!PQUEUE_ISEMPTY(expandQueuePtr)) {

    element_t* currentElementPtr = (element_t*)PQUEUE_POP(expandQueuePtr);

    PLIST_INSERT(beforeListPtr, (void*)currentElementPtr); /* no duplicates */
    list_t* neighborListPtr = TMelement_getNeighborListPtr(TM_ARG currentElementPtr);

    list_iter_t it;
    TMLIST_ITER_RESET(&it, neighborListPtr);
    while (TMLIST_ITER_HASNEXT(&it, neighborListPtr)) {
      element_t* neighborElementPtr =
        (element_t*)TMLIST_ITER_NEXT(&it, neighborListPtr);
      TMELEMENT_ISGARBAGE(neighborElementPtr); /* so we can detect conflicts */
      if (!list_find(beforeListPtr, (void*)neighborElementPtr)) {
        if (element_isInCircumCircle(neighborElementPtr, centerCoordinatePtr)) {
          /* This is part of the region */
          if (!isBoundary && (element_getNumEdge(neighborElementPtr) == 1)) {
            /* Encroached on mesh boundary so split it and restart */
            return neighborElementPtr;
          } else {
            /* Continue breadth-first search */
            bool_t isSuccess;
            isSuccess = PQUEUE_PUSH(expandQueuePtr,
                                    (void*)neighborElementPtr);
            assert(isSuccess);
          }
        } else {
          /* This element borders region; save info for retriangulation */
          edge_t* borderEdgePtr =
            TMelement_getCommonEdge(TM_ARG neighborElementPtr, currentElementPtr);
          if (!borderEdgePtr) {
            TM_RESTART();
          }
          PLIST_INSERT(borderListPtr,
                       (void*)borderEdgePtr); /* no duplicates */
          if (!MAP_CONTAINS(edgeMapPtr, borderEdgePtr)) {
            PMAP_INSERT(edgeMapPtr, borderEdgePtr, neighborElementPtr);
          }
        }
      } /* not visited before */
    } /* for each neighbor */

  } /* breadth-first search */

  return NULL;
}
Exemplo n.º 13
0
Arquivo: region.c Projeto: riclas/rstm
/* =============================================================================
 * TMretriangulate
 * -- Returns net amount of elements added to mesh
 * =============================================================================
 */
long
TMretriangulate (TM_ARGDECL
                 element_t* elementPtr,
                 region_t* regionPtr,
                 mesh_t* meshPtr,
                 MAP_T* edgeMapPtr)
{
  vector_t* badVectorPtr = regionPtr->badVectorPtr; /* private */
  list_t* beforeListPtr = regionPtr->beforeListPtr; /* private */
  list_t* borderListPtr = regionPtr->borderListPtr; /* private */
  list_iter_t it;
  long numDelta = 0L;

  assert(edgeMapPtr);

  coordinate_t centerCoordinate = element_getNewPoint(elementPtr);

  /*
   * Remove the old triangles
   */

  TMLIST_ITER_RESET(&it, beforeListPtr);
  while (TMLIST_ITER_HASNEXT(&it, beforeListPtr)) {
    element_t* beforeElementPtr =
      (element_t*)TMLIST_ITER_NEXT(&it, beforeListPtr);
    TMMESH_REMOVE(meshPtr, beforeElementPtr);
  }

  numDelta -= PLIST_GETSIZE(beforeListPtr);

  /*
   * If segment is encroached, split it in half
   */

  if (element_getNumEdge(elementPtr) == 1) {

    coordinate_t coordinates[2];

    edge_t* edgePtr = element_getEdge(elementPtr, 0);
    coordinates[0] = centerCoordinate;

    coordinates[1] = *(coordinate_t*)(edgePtr->firstPtr);
    element_t* aElementPtr = TMELEMENT_ALLOC(coordinates, 2);
    assert(aElementPtr);
    TMMESH_INSERT(meshPtr, aElementPtr, edgeMapPtr);

    coordinates[1] = *(coordinate_t*)(edgePtr->secondPtr);
    element_t* bElementPtr = TMELEMENT_ALLOC(coordinates, 2);
    assert(bElementPtr);
    TMMESH_INSERT(meshPtr, bElementPtr, edgeMapPtr);

    bool_t status;
    status = TMMESH_REMOVEBOUNDARY(meshPtr, element_getEdge(elementPtr, 0));
    assert(status);
    status = TMMESH_INSERTBOUNDARY(meshPtr, element_getEdge(aElementPtr, 0));
    assert(status);
    status = TMMESH_INSERTBOUNDARY(meshPtr, element_getEdge(bElementPtr, 0));
    assert(status);

    numDelta += 2;
  }

  /*
   * Insert the new triangles. These are contructed using the new
   * point and the two points from the border segment.
   */

  list_iter_reset(&it, borderListPtr);
  while (list_iter_hasNext(&it, borderListPtr)) {
    element_t* afterElementPtr;
    coordinate_t coordinates[3];
    edge_t* borderEdgePtr = (edge_t*)list_iter_next(&it, borderListPtr);
    assert(borderEdgePtr);
    coordinates[0] = centerCoordinate;
    coordinates[1] = *(coordinate_t*)(borderEdgePtr->firstPtr);
    coordinates[2] = *(coordinate_t*)(borderEdgePtr->secondPtr);
    afterElementPtr = TMELEMENT_ALLOC(coordinates, 3);
    assert(afterElementPtr);
    TMMESH_INSERT(meshPtr, afterElementPtr, edgeMapPtr);
    if (element_isBad(afterElementPtr)) {
      TMaddToBadVector(TM_ARG  badVectorPtr, afterElementPtr);
    }
  }

  numDelta += PLIST_GETSIZE(borderListPtr);

  return numDelta;
}