1 #include <petsc/private/dmpleximpl.h> /*I "petscdmplex.h" I*/
2
DMPlexPointQueueCreate(PetscInt size,DMPlexPointQueue * queue)3 PetscErrorCode DMPlexPointQueueCreate(PetscInt size, DMPlexPointQueue *queue)
4 {
5 DMPlexPointQueue q;
6
7 PetscFunctionBegin;
8 PetscCheck(size >= 0, PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE, "Queue size %" PetscInt_FMT " must be non-negative", size);
9 PetscCall(PetscCalloc1(1, &q));
10 q->size = size;
11 PetscCall(PetscMalloc1(q->size, &q->points));
12 q->num = 0;
13 q->front = 0;
14 q->back = q->size - 1;
15 *queue = q;
16 PetscFunctionReturn(PETSC_SUCCESS);
17 }
18
DMPlexPointQueueDestroy(DMPlexPointQueue * queue)19 PetscErrorCode DMPlexPointQueueDestroy(DMPlexPointQueue *queue)
20 {
21 DMPlexPointQueue q = *queue;
22
23 PetscFunctionBegin;
24 PetscCall(PetscFree(q->points));
25 PetscCall(PetscFree(q));
26 *queue = NULL;
27 PetscFunctionReturn(PETSC_SUCCESS);
28 }
29
DMPlexPointQueueEnsureSize(DMPlexPointQueue queue)30 PetscErrorCode DMPlexPointQueueEnsureSize(DMPlexPointQueue queue)
31 {
32 PetscFunctionBegin;
33 if (queue->num < queue->size) PetscFunctionReturn(PETSC_SUCCESS);
34 queue->size *= 2;
35 PetscCall(PetscRealloc(queue->size * sizeof(PetscInt), &queue->points));
36 PetscFunctionReturn(PETSC_SUCCESS);
37 }
38
DMPlexPointQueueEnqueue(DMPlexPointQueue queue,PetscInt p)39 PetscErrorCode DMPlexPointQueueEnqueue(DMPlexPointQueue queue, PetscInt p)
40 {
41 PetscFunctionBegin;
42 PetscCall(DMPlexPointQueueEnsureSize(queue));
43 queue->back = (queue->back + 1) % queue->size;
44 queue->points[queue->back] = p;
45 ++queue->num;
46 PetscFunctionReturn(PETSC_SUCCESS);
47 }
48
DMPlexPointQueueDequeue(DMPlexPointQueue queue,PetscInt * p)49 PetscErrorCode DMPlexPointQueueDequeue(DMPlexPointQueue queue, PetscInt *p)
50 {
51 PetscFunctionBegin;
52 PetscCheck(queue->num, PETSC_COMM_SELF, PETSC_ERR_ARG_WRONGSTATE, "Cannot dequeue from an empty queue");
53 *p = queue->points[queue->front];
54 queue->front = (queue->front + 1) % queue->size;
55 --queue->num;
56 PetscFunctionReturn(PETSC_SUCCESS);
57 }
58
DMPlexPointQueueFront(DMPlexPointQueue queue,PetscInt * p)59 PetscErrorCode DMPlexPointQueueFront(DMPlexPointQueue queue, PetscInt *p)
60 {
61 PetscFunctionBegin;
62 PetscCheck(queue->num, PETSC_COMM_SELF, PETSC_ERR_ARG_WRONGSTATE, "Cannot get the front of an empty queue");
63 *p = queue->points[queue->front];
64 PetscFunctionReturn(PETSC_SUCCESS);
65 }
66
DMPlexPointQueueBack(DMPlexPointQueue queue,PetscInt * p)67 PetscErrorCode DMPlexPointQueueBack(DMPlexPointQueue queue, PetscInt *p)
68 {
69 PetscFunctionBegin;
70 PetscCheck(queue->num, PETSC_COMM_SELF, PETSC_ERR_ARG_WRONGSTATE, "Cannot get the back of an empty queue");
71 *p = queue->points[queue->back];
72 PetscFunctionReturn(PETSC_SUCCESS);
73 }
74
DMPlexPointQueueEmpty(DMPlexPointQueue queue)75 PetscBool DMPlexPointQueueEmpty(DMPlexPointQueue queue)
76 {
77 if (!queue->num) return PETSC_TRUE;
78 return PETSC_FALSE;
79 }
80
DMPlexPointQueueEmptyCollective(PetscObject obj,DMPlexPointQueue queue,PetscBool * empty)81 PetscErrorCode DMPlexPointQueueEmptyCollective(PetscObject obj, DMPlexPointQueue queue, PetscBool *empty)
82 {
83 PetscFunctionBeginHot;
84 *empty = DMPlexPointQueueEmpty(queue);
85 PetscCallMPI(MPIU_Allreduce(MPI_IN_PLACE, empty, 1, MPI_C_BOOL, MPI_LAND, PetscObjectComm(obj)));
86 PetscFunctionReturn(PETSC_SUCCESS);
87 }
88